diff options
author | Christof Schmitt <christof.schmitt@de.ibm.com> | 2007-12-20 06:30:26 -0500 |
---|---|---|
committer | James Bottomley <James.Bottomley@HansenPartnership.com> | 2008-01-11 19:29:06 -0500 |
commit | ba1724202aafed4bbc4a239ac6fb433f454fddea (patch) | |
tree | 5a39a935d50dcb555bbe06450443c428d03b82df | |
parent | 3f0ca62add34010241db682e63bb68ba765bf4a9 (diff) |
[SCSI] zfcp: Hold queue lock when checking port/unit handle for FCP command
We need to hold the queue-lock when checking whether we still have a valid
unit/port handle for the FCP command, i.e whether we can issue this request for
this unit/port. If the error recovery is about to close this unit/port, then it
competes for the queue-lock. If the close request issued by the error recovery
wins, then it is guaranteed that this unit/port has been blocked for other
requests.
Signed-off-by: Christof Schmitt <christof.schmitt@de.ibm.com>
Signed-off-by: Martin Peschke <mp3@de.ibm.com>
Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
-rw-r--r-- | drivers/s390/scsi/zfcp_fsf.c | 7 | ||||
-rw-r--r-- | drivers/s390/scsi/zfcp_scsi.c | 8 |
2 files changed, 10 insertions, 5 deletions
diff --git a/drivers/s390/scsi/zfcp_fsf.c b/drivers/s390/scsi/zfcp_fsf.c index 908e8b2107c1..17c251cb10aa 100644 --- a/drivers/s390/scsi/zfcp_fsf.c +++ b/drivers/s390/scsi/zfcp_fsf.c | |||
@@ -3593,6 +3593,12 @@ zfcp_fsf_send_fcp_command_task(struct zfcp_adapter *adapter, | |||
3593 | goto failed_req_create; | 3593 | goto failed_req_create; |
3594 | } | 3594 | } |
3595 | 3595 | ||
3596 | if (unlikely(!atomic_test_mask(ZFCP_STATUS_COMMON_UNBLOCKED, | ||
3597 | &unit->status))) { | ||
3598 | retval = -EBUSY; | ||
3599 | goto unit_blocked; | ||
3600 | } | ||
3601 | |||
3596 | zfcp_unit_get(unit); | 3602 | zfcp_unit_get(unit); |
3597 | fsf_req->unit = unit; | 3603 | fsf_req->unit = unit; |
3598 | 3604 | ||
@@ -3733,6 +3739,7 @@ zfcp_fsf_send_fcp_command_task(struct zfcp_adapter *adapter, | |||
3733 | send_failed: | 3739 | send_failed: |
3734 | no_fit: | 3740 | no_fit: |
3735 | failed_scsi_cmnd: | 3741 | failed_scsi_cmnd: |
3742 | unit_blocked: | ||
3736 | zfcp_unit_put(unit); | 3743 | zfcp_unit_put(unit); |
3737 | zfcp_fsf_req_free(fsf_req); | 3744 | zfcp_fsf_req_free(fsf_req); |
3738 | fsf_req = NULL; | 3745 | fsf_req = NULL; |
diff --git a/drivers/s390/scsi/zfcp_scsi.c b/drivers/s390/scsi/zfcp_scsi.c index 3298fd35000c..b9daf5c05862 100644 --- a/drivers/s390/scsi/zfcp_scsi.c +++ b/drivers/s390/scsi/zfcp_scsi.c | |||
@@ -258,8 +258,9 @@ zfcp_scsi_command_async(struct zfcp_adapter *adapter, struct zfcp_unit *unit, | |||
258 | goto out; | 258 | goto out; |
259 | } | 259 | } |
260 | 260 | ||
261 | if (unlikely( | 261 | tmp = zfcp_fsf_send_fcp_command_task(adapter, unit, scpnt, use_timer, |
262 | !atomic_test_mask(ZFCP_STATUS_COMMON_UNBLOCKED, &unit->status))) { | 262 | ZFCP_REQ_AUTO_CLEANUP); |
263 | if (unlikely(tmp == -EBUSY)) { | ||
263 | ZFCP_LOG_DEBUG("adapter %s not ready or unit 0x%016Lx " | 264 | ZFCP_LOG_DEBUG("adapter %s not ready or unit 0x%016Lx " |
264 | "on port 0x%016Lx in recovery\n", | 265 | "on port 0x%016Lx in recovery\n", |
265 | zfcp_get_busid_by_unit(unit), | 266 | zfcp_get_busid_by_unit(unit), |
@@ -268,9 +269,6 @@ zfcp_scsi_command_async(struct zfcp_adapter *adapter, struct zfcp_unit *unit, | |||
268 | goto out; | 269 | goto out; |
269 | } | 270 | } |
270 | 271 | ||
271 | tmp = zfcp_fsf_send_fcp_command_task(adapter, unit, scpnt, use_timer, | ||
272 | ZFCP_REQ_AUTO_CLEANUP); | ||
273 | |||
274 | if (unlikely(tmp < 0)) { | 272 | if (unlikely(tmp < 0)) { |
275 | ZFCP_LOG_DEBUG("error: initiation of Send FCP Cmnd failed\n"); | 273 | ZFCP_LOG_DEBUG("error: initiation of Send FCP Cmnd failed\n"); |
276 | retval = SCSI_MLQUEUE_HOST_BUSY; | 274 | retval = SCSI_MLQUEUE_HOST_BUSY; |