aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/qla2xxx
diff options
context:
space:
mode:
authorAnirban Chakraborty <anirban.chakraborty@qlogic.com>2009-08-05 12:18:40 -0400
committerJames Bottomley <James.Bottomley@suse.de>2009-08-22 18:52:20 -0400
commit7163ea815170f8c5d56ead27d7e6fa3fa1f9844b (patch)
treef85fafb74828242c1be343caa020a45753ec1dfa /drivers/scsi/qla2xxx
parent09ccbcc628f71e7f57b4a96982ad1bb2084391d8 (diff)
[SCSI] qla2xxx: Fix to ensure driver works in sinlge queue mode if multiqueue fails
When the multiqueue mode fails to work, the driver falls back on single queue mode. This ensures that the firmware is reinitialized with single queue options and all the resources are readjusted accordingly. Signed-off-by: Anirban Chakraborty <anirban.chakraborty@qlogic.com> Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com> Signed-off-by: James Bottomley <James.Bottomley@suse.de>
Diffstat (limited to 'drivers/scsi/qla2xxx')
-rw-r--r--drivers/scsi/qla2xxx/qla_attr.c4
-rw-r--r--drivers/scsi/qla2xxx/qla_def.h1
-rw-r--r--drivers/scsi/qla2xxx/qla_init.c5
-rw-r--r--drivers/scsi/qla2xxx/qla_iocb.c2
-rw-r--r--drivers/scsi/qla2xxx/qla_mbx.c4
-rw-r--r--drivers/scsi/qla2xxx/qla_os.c23
6 files changed, 27 insertions, 12 deletions
diff --git a/drivers/scsi/qla2xxx/qla_attr.c b/drivers/scsi/qla2xxx/qla_attr.c
index 0f8796201504..5b0a222241bb 100644
--- a/drivers/scsi/qla2xxx/qla_attr.c
+++ b/drivers/scsi/qla2xxx/qla_attr.c
@@ -1670,7 +1670,7 @@ qla24xx_vport_create(struct fc_vport *fc_vport, bool disable)
1670 1670
1671 qla24xx_vport_disable(fc_vport, disable); 1671 qla24xx_vport_disable(fc_vport, disable);
1672 1672
1673 if (ql2xmultique_tag) { 1673 if (ha->flags.cpu_affinity_enabled) {
1674 req = ha->req_q_map[1]; 1674 req = ha->req_q_map[1];
1675 goto vport_queue; 1675 goto vport_queue;
1676 } else if (ql2xmaxqueues == 1 || !ha->npiv_info) 1676 } else if (ql2xmaxqueues == 1 || !ha->npiv_info)
@@ -1743,7 +1743,7 @@ qla24xx_vport_delete(struct fc_vport *fc_vport)
1743 vha->host_no, vha->vp_idx, vha)); 1743 vha->host_no, vha->vp_idx, vha));
1744 } 1744 }
1745 1745
1746 if (vha->req->id && !ql2xmultique_tag) { 1746 if (vha->req->id && !ha->flags.cpu_affinity_enabled) {
1747 if (qla25xx_delete_req_que(vha, vha->req) != QLA_SUCCESS) 1747 if (qla25xx_delete_req_que(vha, vha->req) != QLA_SUCCESS)
1748 qla_printk(KERN_WARNING, ha, 1748 qla_printk(KERN_WARNING, ha,
1749 "Queue delete failed.\n"); 1749 "Queue delete failed.\n");
diff --git a/drivers/scsi/qla2xxx/qla_def.h b/drivers/scsi/qla2xxx/qla_def.h
index 9fde8bfe7607..68ab28c8152b 100644
--- a/drivers/scsi/qla2xxx/qla_def.h
+++ b/drivers/scsi/qla2xxx/qla_def.h
@@ -2224,6 +2224,7 @@ struct qla_hw_data {
2224 uint32_t chip_reset_done :1; 2224 uint32_t chip_reset_done :1;
2225 uint32_t port0 :1; 2225 uint32_t port0 :1;
2226 uint32_t running_gold_fw :1; 2226 uint32_t running_gold_fw :1;
2227 uint32_t cpu_affinity_enabled :1;
2227 } flags; 2228 } flags;
2228 2229
2229 /* This spinlock is used to protect "io transactions", you must 2230 /* This spinlock is used to protect "io transactions", you must
diff --git a/drivers/scsi/qla2xxx/qla_init.c b/drivers/scsi/qla2xxx/qla_init.c
index f2ce8e3cc91b..0cbe39e92506 100644
--- a/drivers/scsi/qla2xxx/qla_init.c
+++ b/drivers/scsi/qla2xxx/qla_init.c
@@ -987,7 +987,6 @@ qla2x00_setup_chip(scsi_qla_host_t *vha)
987 ha->phy_version); 987 ha->phy_version);
988 if (rval != QLA_SUCCESS) 988 if (rval != QLA_SUCCESS)
989 goto failed; 989 goto failed;
990
991 ha->flags.npiv_supported = 0; 990 ha->flags.npiv_supported = 0;
992 if (IS_QLA2XXX_MIDTYPE(ha) && 991 if (IS_QLA2XXX_MIDTYPE(ha) &&
993 (ha->fw_attributes & BIT_2)) { 992 (ha->fw_attributes & BIT_2)) {
@@ -3244,7 +3243,7 @@ qla2x00_loop_resync(scsi_qla_host_t *vha)
3244 struct req_que *req; 3243 struct req_que *req;
3245 struct rsp_que *rsp; 3244 struct rsp_que *rsp;
3246 3245
3247 if (ql2xmultique_tag) 3246 if (vha->hw->flags.cpu_affinity_enabled)
3248 req = vha->hw->req_q_map[0]; 3247 req = vha->hw->req_q_map[0];
3249 else 3248 else
3250 req = vha->req; 3249 req = vha->req;
@@ -4264,7 +4263,7 @@ qla24xx_configure_vhba(scsi_qla_host_t *vha)
4264 return -EINVAL; 4263 return -EINVAL;
4265 4264
4266 rval = qla2x00_fw_ready(base_vha); 4265 rval = qla2x00_fw_ready(base_vha);
4267 if (ql2xmultique_tag) 4266 if (ha->flags.cpu_affinity_enabled)
4268 req = ha->req_q_map[0]; 4267 req = ha->req_q_map[0];
4269 else 4268 else
4270 req = vha->req; 4269 req = vha->req;
diff --git a/drivers/scsi/qla2xxx/qla_iocb.c b/drivers/scsi/qla2xxx/qla_iocb.c
index 13396beae2ce..c0ba370b23cf 100644
--- a/drivers/scsi/qla2xxx/qla_iocb.c
+++ b/drivers/scsi/qla2xxx/qla_iocb.c
@@ -852,7 +852,7 @@ static void qla25xx_set_que(srb_t *sp, struct rsp_que **rsp)
852 struct qla_hw_data *ha = sp->fcport->vha->hw; 852 struct qla_hw_data *ha = sp->fcport->vha->hw;
853 int affinity = cmd->request->cpu; 853 int affinity = cmd->request->cpu;
854 854
855 if (ql2xmultique_tag && affinity >= 0 && 855 if (ha->flags.cpu_affinity_enabled && affinity >= 0 &&
856 affinity < ha->max_rsp_queues - 1) 856 affinity < ha->max_rsp_queues - 1)
857 *rsp = ha->rsp_q_map[affinity + 1]; 857 *rsp = ha->rsp_q_map[affinity + 1];
858 else 858 else
diff --git a/drivers/scsi/qla2xxx/qla_mbx.c b/drivers/scsi/qla2xxx/qla_mbx.c
index 8fcd99eeec00..b6202fe118ac 100644
--- a/drivers/scsi/qla2xxx/qla_mbx.c
+++ b/drivers/scsi/qla2xxx/qla_mbx.c
@@ -1507,7 +1507,7 @@ qla24xx_login_fabric(scsi_qla_host_t *vha, uint16_t loop_id, uint8_t domain,
1507 1507
1508 DEBUG11(printk("%s(%ld): entered.\n", __func__, vha->host_no)); 1508 DEBUG11(printk("%s(%ld): entered.\n", __func__, vha->host_no));
1509 1509
1510 if (ql2xmultique_tag) 1510 if (ha->flags.cpu_affinity_enabled)
1511 req = ha->req_q_map[0]; 1511 req = ha->req_q_map[0];
1512 else 1512 else
1513 req = vha->req; 1513 req = vha->req;
@@ -2324,7 +2324,7 @@ __qla24xx_issue_tmf(char *name, uint32_t type, struct fc_port *fcport,
2324 vha = fcport->vha; 2324 vha = fcport->vha;
2325 ha = vha->hw; 2325 ha = vha->hw;
2326 req = vha->req; 2326 req = vha->req;
2327 if (ql2xmultique_tag) 2327 if (ha->flags.cpu_affinity_enabled)
2328 rsp = ha->rsp_q_map[tag + 1]; 2328 rsp = ha->rsp_q_map[tag + 1];
2329 else 2329 else
2330 rsp = req->rsp; 2330 rsp = req->rsp;
diff --git a/drivers/scsi/qla2xxx/qla_os.c b/drivers/scsi/qla2xxx/qla_os.c
index f0396e79b6fa..d7b271339a5c 100644
--- a/drivers/scsi/qla2xxx/qla_os.c
+++ b/drivers/scsi/qla2xxx/qla_os.c
@@ -287,9 +287,12 @@ static int qla25xx_setup_mode(struct scsi_qla_host *vha)
287 int ques, req, ret; 287 int ques, req, ret;
288 struct qla_hw_data *ha = vha->hw; 288 struct qla_hw_data *ha = vha->hw;
289 289
290 if (!(ha->fw_attributes & BIT_6)) {
291 qla_printk(KERN_INFO, ha,
292 "Firmware is not multi-queue capable\n");
293 goto fail;
294 }
290 if (ql2xmultique_tag) { 295 if (ql2xmultique_tag) {
291 /* CPU affinity mode */
292 ha->wq = create_workqueue("qla2xxx_wq");
293 /* create a request queue for IO */ 296 /* create a request queue for IO */
294 options |= BIT_7; 297 options |= BIT_7;
295 req = qla25xx_create_req_que(ha, options, 0, 0, -1, 298 req = qla25xx_create_req_que(ha, options, 0, 0, -1,
@@ -299,6 +302,7 @@ static int qla25xx_setup_mode(struct scsi_qla_host *vha)
299 "Can't create request queue\n"); 302 "Can't create request queue\n");
300 goto fail; 303 goto fail;
301 } 304 }
305 ha->wq = create_workqueue("qla2xxx_wq");
302 vha->req = ha->req_q_map[req]; 306 vha->req = ha->req_q_map[req];
303 options |= BIT_1; 307 options |= BIT_1;
304 for (ques = 1; ques < ha->max_rsp_queues; ques++) { 308 for (ques = 1; ques < ha->max_rsp_queues; ques++) {
@@ -309,6 +313,8 @@ static int qla25xx_setup_mode(struct scsi_qla_host *vha)
309 goto fail2; 313 goto fail2;
310 } 314 }
311 } 315 }
316 ha->flags.cpu_affinity_enabled = 1;
317
312 DEBUG2(qla_printk(KERN_INFO, ha, 318 DEBUG2(qla_printk(KERN_INFO, ha,
313 "CPU affinity mode enabled, no. of response" 319 "CPU affinity mode enabled, no. of response"
314 " queues:%d, no. of request queues:%d\n", 320 " queues:%d, no. of request queues:%d\n",
@@ -317,8 +323,13 @@ static int qla25xx_setup_mode(struct scsi_qla_host *vha)
317 return 0; 323 return 0;
318fail2: 324fail2:
319 qla25xx_delete_queues(vha); 325 qla25xx_delete_queues(vha);
326 destroy_workqueue(ha->wq);
327 ha->wq = NULL;
320fail: 328fail:
321 ha->mqenable = 0; 329 ha->mqenable = 0;
330 kfree(ha->req_q_map);
331 kfree(ha->rsp_q_map);
332 ha->max_req_queues = ha->max_rsp_queues = 1;
322 return 1; 333 return 1;
323} 334}
324 335
@@ -1923,6 +1934,7 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id)
1923 if (ret) 1934 if (ret)
1924 goto probe_init_failed; 1935 goto probe_init_failed;
1925 /* Alloc arrays of request and response ring ptrs */ 1936 /* Alloc arrays of request and response ring ptrs */
1937que_init:
1926 if (!qla2x00_alloc_queues(ha)) { 1938 if (!qla2x00_alloc_queues(ha)) {
1927 qla_printk(KERN_WARNING, ha, 1939 qla_printk(KERN_WARNING, ha,
1928 "[ERROR] Failed to allocate memory for queue" 1940 "[ERROR] Failed to allocate memory for queue"
@@ -1959,11 +1971,14 @@ qla2x00_probe_one(struct pci_dev *pdev, const struct pci_device_id *id)
1959 goto probe_failed; 1971 goto probe_failed;
1960 } 1972 }
1961 1973
1962 if (ha->mqenable) 1974 if (ha->mqenable) {
1963 if (qla25xx_setup_mode(base_vha)) 1975 if (qla25xx_setup_mode(base_vha)) {
1964 qla_printk(KERN_WARNING, ha, 1976 qla_printk(KERN_WARNING, ha,
1965 "Can't create queues, falling back to single" 1977 "Can't create queues, falling back to single"
1966 " queue mode\n"); 1978 " queue mode\n");
1979 goto que_init;
1980 }
1981 }
1967 1982
1968 if (ha->flags.running_gold_fw) 1983 if (ha->flags.running_gold_fw)
1969 goto skip_dpc; 1984 goto skip_dpc;