aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorManish Rangankar <manish.rangankar@qlogic.com>2011-10-07 19:55:46 -0400
committerJames Bottomley <JBottomley@Parallels.com>2011-10-16 12:10:06 -0400
commit736cf369c9a514a9ed596e97375c49ef1fdf920a (patch)
tree1b5a9bd343152f315982125edd36a33f2c1b3fde /drivers
parent166dd20d794e7885b23c8d5fc533949ed82cc337 (diff)
[SCSI] qla4xxx: Clear DDB map index on the basis of AEN.
Unable to login to session if login-logout issued consecutively for multiple sessions. Solution is to clear idx in DDB map on the basis of no-active connection asynchronous event (AEN). JIRA Key: UPSISCSI-135 Signed-off-by: Manish Rangankar <manish.rangankar@qlogic.com> Signed-off-by: Vikas Chaudhary <vikas.chaudhary@qlogic.com> Reviewed-by: Mike Christie <michaelc@cs.wisc.edu> Signed-off-by: James Bottomley <JBottomley@Parallels.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/scsi/qla4xxx/ql4_init.c12
-rw-r--r--drivers/scsi/qla4xxx/ql4_os.c11
2 files changed, 14 insertions, 9 deletions
diff --git a/drivers/scsi/qla4xxx/ql4_init.c b/drivers/scsi/qla4xxx/ql4_init.c
index 064a3a311e77..ca155bb9fd0a 100644
--- a/drivers/scsi/qla4xxx/ql4_init.c
+++ b/drivers/scsi/qla4xxx/ql4_init.c
@@ -880,6 +880,10 @@ int qla4xxx_process_ddb_changed(struct scsi_qla_host *ha, uint32_t fw_ddb_index,
880 if (ddb_entry == NULL) { 880 if (ddb_entry == NULL) {
881 ql4_printk(KERN_ERR, ha, "%s: No ddb_entry at FW index [%d]\n", 881 ql4_printk(KERN_ERR, ha, "%s: No ddb_entry at FW index [%d]\n",
882 __func__, fw_ddb_index); 882 __func__, fw_ddb_index);
883
884 if (state == DDB_DS_NO_CONNECTION_ACTIVE)
885 clear_bit(fw_ddb_index, ha->ddb_idx_map);
886
883 goto exit_ddb_event; 887 goto exit_ddb_event;
884 } 888 }
885 889
@@ -910,7 +914,8 @@ int qla4xxx_process_ddb_changed(struct scsi_qla_host *ha, uint32_t fw_ddb_index,
910 } 914 }
911 break; 915 break;
912 case DDB_DS_SESSION_ACTIVE: 916 case DDB_DS_SESSION_ACTIVE:
913 if (state == DDB_DS_SESSION_FAILED) { 917 switch (state) {
918 case DDB_DS_SESSION_FAILED:
914 /* 919 /*
915 * iscsi_session failure will cause userspace to 920 * iscsi_session failure will cause userspace to
916 * stop the connection which in turn would block the 921 * stop the connection which in turn would block the
@@ -919,6 +924,11 @@ int qla4xxx_process_ddb_changed(struct scsi_qla_host *ha, uint32_t fw_ddb_index,
919 iscsi_session_failure(ddb_entry->sess->dd_data, 924 iscsi_session_failure(ddb_entry->sess->dd_data,
920 ISCSI_ERR_CONN_FAILED); 925 ISCSI_ERR_CONN_FAILED);
921 status = QLA_SUCCESS; 926 status = QLA_SUCCESS;
927 break;
928 case DDB_DS_NO_CONNECTION_ACTIVE:
929 clear_bit(fw_ddb_index, ha->ddb_idx_map);
930 status = QLA_SUCCESS;
931 break;
922 } 932 }
923 break; 933 break;
924 default: 934 default:
diff --git a/drivers/scsi/qla4xxx/ql4_os.c b/drivers/scsi/qla4xxx/ql4_os.c
index 5266d97640cb..bea78a7f6bc1 100644
--- a/drivers/scsi/qla4xxx/ql4_os.c
+++ b/drivers/scsi/qla4xxx/ql4_os.c
@@ -1004,6 +1004,7 @@ qla4xxx_session_create(struct iscsi_endpoint *ep,
1004 qla_ep = ep->dd_data; 1004 qla_ep = ep->dd_data;
1005 dst_addr = (struct sockaddr *)&qla_ep->dst_addr; 1005 dst_addr = (struct sockaddr *)&qla_ep->dst_addr;
1006 ha = to_qla_host(qla_ep->host); 1006 ha = to_qla_host(qla_ep->host);
1007
1007get_ddb_index: 1008get_ddb_index:
1008 ddb_index = find_first_zero_bit(ha->ddb_idx_map, MAX_DDB_ENTRIES); 1009 ddb_index = find_first_zero_bit(ha->ddb_idx_map, MAX_DDB_ENTRIES);
1009 1010
@@ -1063,6 +1064,8 @@ static void qla4xxx_session_destroy(struct iscsi_cls_session *cls_sess)
1063 ddb_entry = sess->dd_data; 1064 ddb_entry = sess->dd_data;
1064 ha = ddb_entry->ha; 1065 ha = ddb_entry->ha;
1065 1066
1067 qla4xxx_clear_ddb_entry(ha, ddb_entry->fw_ddb_index);
1068
1066 spin_lock_irqsave(&ha->hardware_lock, flags); 1069 spin_lock_irqsave(&ha->hardware_lock, flags);
1067 qla4xxx_free_ddb(ha, ddb_entry); 1070 qla4xxx_free_ddb(ha, ddb_entry);
1068 spin_unlock_irqrestore(&ha->hardware_lock, flags); 1071 spin_unlock_irqrestore(&ha->hardware_lock, flags);
@@ -1183,14 +1186,6 @@ static void qla4xxx_conn_destroy(struct iscsi_cls_conn *cls_conn)
1183 options = LOGOUT_OPTION_CLOSE_SESSION; 1186 options = LOGOUT_OPTION_CLOSE_SESSION;
1184 if (qla4xxx_session_logout_ddb(ha, ddb_entry, options) == QLA_ERROR) 1187 if (qla4xxx_session_logout_ddb(ha, ddb_entry, options) == QLA_ERROR)
1185 ql4_printk(KERN_ERR, ha, "%s: Logout failed\n", __func__); 1188 ql4_printk(KERN_ERR, ha, "%s: Logout failed\n", __func__);
1186 else
1187 qla4xxx_clear_ddb_entry(ha, ddb_entry->fw_ddb_index);
1188
1189 /*
1190 * Clear the DDB bit so that next login can use the bit
1191 * if FW is not clearing the DDB entry then set DDB will fail anyways
1192 */
1193 clear_bit(ddb_entry->fw_ddb_index, ha->ddb_idx_map);
1194} 1189}
1195 1190
1196static void qla4xxx_task_work(struct work_struct *wdata) 1191static void qla4xxx_task_work(struct work_struct *wdata)