aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/s390/scsi/zfcp_aux.c23
-rw-r--r--drivers/s390/scsi/zfcp_dbf.c2
-rw-r--r--drivers/s390/scsi/zfcp_def.h4
-rw-r--r--drivers/s390/scsi/zfcp_erp.c19
-rw-r--r--drivers/s390/scsi/zfcp_ext.h1
-rw-r--r--drivers/s390/scsi/zfcp_fsf.c18
6 files changed, 32 insertions, 35 deletions
diff --git a/drivers/s390/scsi/zfcp_aux.c b/drivers/s390/scsi/zfcp_aux.c
index d23027a2f2f0..41635b13ccb1 100644
--- a/drivers/s390/scsi/zfcp_aux.c
+++ b/drivers/s390/scsi/zfcp_aux.c
@@ -970,6 +970,27 @@ static void zfcp_dummy_release(struct device *dev)
970 return; 970 return;
971} 971}
972 972
973int zfcp_status_read_refill(struct zfcp_adapter *adapter)
974{
975 while (atomic_read(&adapter->stat_miss) > 0)
976 if (zfcp_fsf_status_read(adapter, ZFCP_WAIT_FOR_SBAL))
977 break;
978 else
979 atomic_dec(&adapter->stat_miss);
980
981 if (ZFCP_STATUS_READS_RECOM <= atomic_read(&adapter->stat_miss)) {
982 zfcp_erp_adapter_reopen(adapter, 0, 103, NULL);
983 return 1;
984 }
985 return 0;
986}
987
988static void _zfcp_status_read_scheduler(struct work_struct *work)
989{
990 zfcp_status_read_refill(container_of(work, struct zfcp_adapter,
991 stat_work));
992}
993
973/* 994/*
974 * Enqueues an adapter at the end of the adapter list in the driver data. 995 * Enqueues an adapter at the end of the adapter list in the driver data.
975 * All adapter internal structures are set up. 996 * All adapter internal structures are set up.
@@ -1063,6 +1084,7 @@ zfcp_adapter_enqueue(struct ccw_device *ccw_device)
1063 1084
1064 /* initialize lock of associated request queue */ 1085 /* initialize lock of associated request queue */
1065 rwlock_init(&adapter->request_queue.queue_lock); 1086 rwlock_init(&adapter->request_queue.queue_lock);
1087 INIT_WORK(&adapter->stat_work, _zfcp_status_read_scheduler);
1066 1088
1067 /* mark adapter unusable as long as sysfs registration is not complete */ 1089 /* mark adapter unusable as long as sysfs registration is not complete */
1068 atomic_set_mask(ZFCP_STATUS_COMMON_REMOVE, &adapter->status); 1090 atomic_set_mask(ZFCP_STATUS_COMMON_REMOVE, &adapter->status);
@@ -1123,6 +1145,7 @@ zfcp_adapter_dequeue(struct zfcp_adapter *adapter)
1123 int retval = 0; 1145 int retval = 0;
1124 unsigned long flags; 1146 unsigned long flags;
1125 1147
1148 cancel_work_sync(&adapter->stat_work);
1126 zfcp_adapter_scsi_unregister(adapter); 1149 zfcp_adapter_scsi_unregister(adapter);
1127 device_unregister(&adapter->generic_services); 1150 device_unregister(&adapter->generic_services);
1128 zfcp_sysfs_adapter_remove_files(&adapter->ccw_device->dev); 1151 zfcp_sysfs_adapter_remove_files(&adapter->ccw_device->dev);
diff --git a/drivers/s390/scsi/zfcp_dbf.c b/drivers/s390/scsi/zfcp_dbf.c
index c8bad675dbd1..1710c12a32c4 100644
--- a/drivers/s390/scsi/zfcp_dbf.c
+++ b/drivers/s390/scsi/zfcp_dbf.c
@@ -268,7 +268,7 @@ void zfcp_hba_dbf_event_fsf_unsol(const char *tag, struct zfcp_adapter *adapter,
268 strncpy(rec->tag, "stat", ZFCP_DBF_TAG_SIZE); 268 strncpy(rec->tag, "stat", ZFCP_DBF_TAG_SIZE);
269 strncpy(rec->tag2, tag, ZFCP_DBF_TAG_SIZE); 269 strncpy(rec->tag2, tag, ZFCP_DBF_TAG_SIZE);
270 270
271 rec->u.status.failed = adapter->status_read_failed; 271 rec->u.status.failed = atomic_read(&adapter->stat_miss);
272 if (status_buffer != NULL) { 272 if (status_buffer != NULL) {
273 rec->u.status.status_type = status_buffer->status_type; 273 rec->u.status.status_type = status_buffer->status_type;
274 rec->u.status.status_subtype = status_buffer->status_subtype; 274 rec->u.status.status_subtype = status_buffer->status_subtype;
diff --git a/drivers/s390/scsi/zfcp_def.h b/drivers/s390/scsi/zfcp_def.h
index 306fcd0cae31..adfbbb07448a 100644
--- a/drivers/s390/scsi/zfcp_def.h
+++ b/drivers/s390/scsi/zfcp_def.h
@@ -136,7 +136,6 @@ zfcp_address_to_sg(void *address, struct scatterlist *list, unsigned int size)
136#define ZFCP_QTCB_VERSION FSF_QTCB_CURRENT_VERSION 136#define ZFCP_QTCB_VERSION FSF_QTCB_CURRENT_VERSION
137/* ATTENTION: value must not be used by hardware */ 137/* ATTENTION: value must not be used by hardware */
138#define FSF_QTCB_UNSOLICITED_STATUS 0x6305 138#define FSF_QTCB_UNSOLICITED_STATUS 0x6305
139#define ZFCP_STATUS_READ_FAILED_THRESHOLD 3
140#define ZFCP_STATUS_READS_RECOM FSF_STATUS_READS_RECOM 139#define ZFCP_STATUS_READS_RECOM FSF_STATUS_READS_RECOM
141 140
142/* Do 1st retry in 1 second, then double the timeout for each following retry */ 141/* Do 1st retry in 1 second, then double the timeout for each following retry */
@@ -759,7 +758,8 @@ struct zfcp_adapter {
759 rwlock_t abort_lock; /* Protects against SCSI 758 rwlock_t abort_lock; /* Protects against SCSI
760 stack abort/command 759 stack abort/command
761 completion races */ 760 completion races */
762 u16 status_read_failed; /* # failed status reads */ 761 atomic_t stat_miss; /* # missing status reads*/
762 struct work_struct stat_work;
763 atomic_t status; /* status of this adapter */ 763 atomic_t status; /* status of this adapter */
764 struct list_head erp_ready_head; /* error recovery for this 764 struct list_head erp_ready_head; /* error recovery for this
765 adapter/devices */ 765 adapter/devices */
diff --git a/drivers/s390/scsi/zfcp_erp.c b/drivers/s390/scsi/zfcp_erp.c
index 805484658dd9..55a4fdc42626 100644
--- a/drivers/s390/scsi/zfcp_erp.c
+++ b/drivers/s390/scsi/zfcp_erp.c
@@ -2139,25 +2139,10 @@ static int
2139zfcp_erp_adapter_strategy_open_fsf_statusread(struct zfcp_erp_action 2139zfcp_erp_adapter_strategy_open_fsf_statusread(struct zfcp_erp_action
2140 *erp_action) 2140 *erp_action)
2141{ 2141{
2142 int retval = ZFCP_ERP_SUCCEEDED;
2143 int temp_ret;
2144 struct zfcp_adapter *adapter = erp_action->adapter; 2142 struct zfcp_adapter *adapter = erp_action->adapter;
2145 int i;
2146 2143
2147 adapter->status_read_failed = 0; 2144 atomic_set(&adapter->stat_miss, 16);
2148 for (i = 0; i < ZFCP_STATUS_READS_RECOM; i++) { 2145 return zfcp_status_read_refill(adapter);
2149 temp_ret = zfcp_fsf_status_read(adapter, ZFCP_WAIT_FOR_SBAL);
2150 if (temp_ret < 0) {
2151 ZFCP_LOG_INFO("error: set-up of unsolicited status "
2152 "notification failed on adapter %s\n",
2153 zfcp_get_busid_by_adapter(adapter));
2154 retval = ZFCP_ERP_FAILED;
2155 i--;
2156 break;
2157 }
2158 }
2159
2160 return retval;
2161} 2146}
2162 2147
2163/* 2148/*
diff --git a/drivers/s390/scsi/zfcp_ext.h b/drivers/s390/scsi/zfcp_ext.h
index 6abf178fda5d..250565794fa5 100644
--- a/drivers/s390/scsi/zfcp_ext.h
+++ b/drivers/s390/scsi/zfcp_ext.h
@@ -92,6 +92,7 @@ extern void zfcp_fsf_start_timer(struct zfcp_fsf_req *, unsigned long);
92extern void zfcp_erp_start_timer(struct zfcp_fsf_req *); 92extern void zfcp_erp_start_timer(struct zfcp_fsf_req *);
93extern void zfcp_fsf_req_dismiss_all(struct zfcp_adapter *); 93extern void zfcp_fsf_req_dismiss_all(struct zfcp_adapter *);
94extern int zfcp_fsf_status_read(struct zfcp_adapter *, int); 94extern int zfcp_fsf_status_read(struct zfcp_adapter *, int);
95extern int zfcp_status_read_refill(struct zfcp_adapter *adapter);
95extern int zfcp_fsf_req_create(struct zfcp_adapter *, u32, int, mempool_t *, 96extern int zfcp_fsf_req_create(struct zfcp_adapter *, u32, int, mempool_t *,
96 unsigned long *, struct zfcp_fsf_req **); 97 unsigned long *, struct zfcp_fsf_req **);
97extern int zfcp_fsf_send_ct(struct zfcp_send_ct *, mempool_t *, 98extern int zfcp_fsf_send_ct(struct zfcp_send_ct *, mempool_t *,
diff --git a/drivers/s390/scsi/zfcp_fsf.c b/drivers/s390/scsi/zfcp_fsf.c
index 1e7136483c1b..b344e8a72f1f 100644
--- a/drivers/s390/scsi/zfcp_fsf.c
+++ b/drivers/s390/scsi/zfcp_fsf.c
@@ -1029,21 +1029,9 @@ zfcp_fsf_status_read_handler(struct zfcp_fsf_req *fsf_req)
1029 * FIXME: 1029 * FIXME:
1030 * allocation failure possible? (Is this code needed?) 1030 * allocation failure possible? (Is this code needed?)
1031 */ 1031 */
1032 retval = zfcp_fsf_status_read(adapter, 0); 1032
1033 if (retval < 0) { 1033 atomic_inc(&adapter->stat_miss);
1034 ZFCP_LOG_INFO("Failed to create unsolicited status read " 1034 schedule_work(&adapter->stat_work);
1035 "request for the adapter %s.\n",
1036 zfcp_get_busid_by_adapter(adapter));
1037 /* temporary fix to avoid status read buffer shortage */
1038 adapter->status_read_failed++;
1039 if ((ZFCP_STATUS_READS_RECOM - adapter->status_read_failed)
1040 < ZFCP_STATUS_READ_FAILED_THRESHOLD) {
1041 ZFCP_LOG_INFO("restart adapter %s due to status read "
1042 "buffer shortage\n",
1043 zfcp_get_busid_by_adapter(adapter));
1044 zfcp_erp_adapter_reopen(adapter, 0, 103, fsf_req);
1045 }
1046 }
1047 out: 1035 out:
1048 return retval; 1036 return retval;
1049} 1037}