Commit 5601236b authored by Michael Hernandez's avatar Michael Hernandez Committed by Martin K. Petersen

scsi: qla2xxx: Add Block Multi Queue functionality.

Tell the SCSI layer how many hardware queues we have based on the number
of max queue pairs created. The number of max queue pairs created will
depend on number of MSI-X vector count.

This feature can be turned on via CONFIG_SCSI_MQ_DEFAULT or passing
scsi_mod.use_blk_mq=Y as a parameter to the kernel
Reviewed-by: default avatarHannes Reinecke <hare@suse.com>
Signed-off-by: default avatarSawan Chandak <sawan.chandak@cavium.com>
Signed-off-by: default avatarMichael Hernandez <michael.hernandez@cavium.com>
Signed-off-by: default avatarHimanshu Madhani <himanshu.madhani@cavium.com>
Reviewed-by: default avatarChristoph Hellwig <hch@lst.de>
Signed-off-by: default avatarMartin K. Petersen <martin.petersen@oracle.com>
parent d7459527
...@@ -13,6 +13,7 @@ ...@@ -13,6 +13,7 @@
#include <linux/mutex.h> #include <linux/mutex.h>
#include <linux/kobject.h> #include <linux/kobject.h>
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/blk-mq-pci.h>
#include <scsi/scsi_tcq.h> #include <scsi/scsi_tcq.h>
#include <scsi/scsicam.h> #include <scsi/scsicam.h>
#include <scsi/scsi_transport.h> #include <scsi/scsi_transport.h>
...@@ -254,6 +255,7 @@ static int qla2xxx_eh_host_reset(struct scsi_cmnd *); ...@@ -254,6 +255,7 @@ static int qla2xxx_eh_host_reset(struct scsi_cmnd *);
static void qla2x00_clear_drv_active(struct qla_hw_data *); static void qla2x00_clear_drv_active(struct qla_hw_data *);
static void qla2x00_free_device(scsi_qla_host_t *); static void qla2x00_free_device(scsi_qla_host_t *);
static void qla83xx_disable_laser(scsi_qla_host_t *vha); static void qla83xx_disable_laser(scsi_qla_host_t *vha);
static int qla2xxx_map_queues(struct Scsi_Host *shost);
struct scsi_host_template qla2xxx_driver_template = { struct scsi_host_template qla2xxx_driver_template = {
.module = THIS_MODULE, .module = THIS_MODULE,
...@@ -273,6 +275,7 @@ struct scsi_host_template qla2xxx_driver_template = { ...@@ -273,6 +275,7 @@ struct scsi_host_template qla2xxx_driver_template = {
.scan_finished = qla2xxx_scan_finished, .scan_finished = qla2xxx_scan_finished,
.scan_start = qla2xxx_scan_start, .scan_start = qla2xxx_scan_start,
.change_queue_depth = scsi_change_queue_depth, .change_queue_depth = scsi_change_queue_depth,
.map_queues = qla2xxx_map_queues,
.this_id = -1, .this_id = -1,
.cmd_per_lun = 3, .cmd_per_lun = 3,
.use_clustering = ENABLE_CLUSTERING, .use_clustering = ENABLE_CLUSTERING,
...@@ -738,15 +741,25 @@ qla2xxx_queuecommand(struct Scsi_Host *host, struct scsi_cmnd *cmd) ...@@ -738,15 +741,25 @@ qla2xxx_queuecommand(struct Scsi_Host *host, struct scsi_cmnd *cmd)
struct scsi_qla_host *base_vha = pci_get_drvdata(ha->pdev); struct scsi_qla_host *base_vha = pci_get_drvdata(ha->pdev);
srb_t *sp; srb_t *sp;
int rval; int rval;
struct qla_qpair *qpair; struct qla_qpair *qpair = NULL;
uint32_t tag;
uint16_t hwq;
if (unlikely(test_bit(UNLOADING, &base_vha->dpc_flags))) { if (unlikely(test_bit(UNLOADING, &base_vha->dpc_flags))) {
cmd->result = DID_NO_CONNECT << 16; cmd->result = DID_NO_CONNECT << 16;
goto qc24_fail_command; goto qc24_fail_command;
} }
if (vha->vp_idx && vha->qpair) { if (ha->mqenable) {
if (shost_use_blk_mq(vha->host)) {
tag = blk_mq_unique_tag(cmd->request);
hwq = blk_mq_unique_tag_to_hwq(tag);
qpair = ha->queue_pair_map[hwq];
} else if (vha->vp_idx && vha->qpair) {
qpair = vha->qpair; qpair = vha->qpair;
}
if (qpair)
return qla2xxx_mqueuecommand(host, cmd, qpair); return qla2xxx_mqueuecommand(host, cmd, qpair);
} }
...@@ -2509,6 +2522,7 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id) ...@@ -2509,6 +2522,7 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id)
uint16_t req_length = 0, rsp_length = 0; uint16_t req_length = 0, rsp_length = 0;
struct req_que *req = NULL; struct req_que *req = NULL;
struct rsp_que *rsp = NULL; struct rsp_que *rsp = NULL;
int i;
bars = pci_select_bars(pdev, IORESOURCE_MEM | IORESOURCE_IO); bars = pci_select_bars(pdev, IORESOURCE_MEM | IORESOURCE_IO);
sht = &qla2xxx_driver_template; sht = &qla2xxx_driver_template;
...@@ -2874,6 +2888,16 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id) ...@@ -2874,6 +2888,16 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id)
goto probe_init_failed; goto probe_init_failed;
} }
if (ha->mqenable && shost_use_blk_mq(host)) {
/* number of hardware queues supported by blk/scsi-mq*/
host->nr_hw_queues = ha->max_qpairs;
ql_dbg(ql_dbg_init, base_vha, 0x0192,
"blk/scsi-mq enabled, HW queues = %d.\n", host->nr_hw_queues);
} else
ql_dbg(ql_dbg_init, base_vha, 0x0193,
"blk/scsi-mq disabled.\n");
qlt_probe_one_stage1(base_vha, ha); qlt_probe_one_stage1(base_vha, ha);
pci_save_state(pdev); pci_save_state(pdev);
...@@ -2965,8 +2989,14 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id) ...@@ -2965,8 +2989,14 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id)
host->can_queue, base_vha->req, host->can_queue, base_vha->req,
base_vha->mgmt_svr_loop_id, host->sg_tablesize); base_vha->mgmt_svr_loop_id, host->sg_tablesize);
if (ha->mqenable) if (ha->mqenable) {
ha->wq = alloc_workqueue("qla2xxx_wq", WQ_MEM_RECLAIM, 1); ha->wq = alloc_workqueue("qla2xxx_wq", WQ_MEM_RECLAIM, 1);
/* Create start of day qpairs for Block MQ */
if (shost_use_blk_mq(host)) {
for (i = 0; i < ha->max_qpairs; i++)
qla2xxx_create_qpair(base_vha, 5, 0);
}
}
if (ha->flags.running_gold_fw) if (ha->flags.running_gold_fw)
goto skip_dpc; goto skip_dpc;
...@@ -6109,6 +6139,13 @@ qla83xx_disable_laser(scsi_qla_host_t *vha) ...@@ -6109,6 +6139,13 @@ qla83xx_disable_laser(scsi_qla_host_t *vha)
qla83xx_wr_reg(vha, reg, data); qla83xx_wr_reg(vha, reg, data);
} }
static int qla2xxx_map_queues(struct Scsi_Host *shost)
{
scsi_qla_host_t *vha = (scsi_qla_host_t *)shost->hostdata;
return blk_mq_pci_map_queues(&shost->tag_set, vha->hw->pdev);
}
static const struct pci_error_handlers qla2xxx_err_handler = { static const struct pci_error_handlers qla2xxx_err_handler = {
.error_detected = qla2xxx_pci_error_detected, .error_detected = qla2xxx_pci_error_detected,
.mmio_enabled = qla2xxx_pci_mmio_enabled, .mmio_enabled = qla2xxx_pci_mmio_enabled,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment