aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi
diff options
context:
space:
mode:
authorJames Smart <James.Smart@Emulex.Com>2008-01-11 01:52:42 -0500
committerJames Bottomley <James.Bottomley@HansenPartnership.com>2008-01-23 12:29:21 -0500
commitfa61a54e48efc8e5c7a6d4680ad8ceb74a5fca84 (patch)
treeabd25d2d2a801bde1891cd4291b4ae05b38f6cdc /drivers/scsi
parent0ff10d46cf0a373c9c855a23cc9383ba4030d8d2 (diff)
[SCSI] lpfc 8.2.4 : Correct abort handler logic
Correct Abort handler logic. It was unconditionally waiting a minimum of 2 seconds rather than looking for abort completion. Signed-off-by: James Smart <James.Smart@emulex.com> Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
Diffstat (limited to 'drivers/scsi')
-rw-r--r--drivers/scsi/lpfc/lpfc_scsi.c38
-rw-r--r--drivers/scsi/lpfc/lpfc_scsi.h1
2 files changed, 29 insertions, 10 deletions
diff --git a/drivers/scsi/lpfc/lpfc_scsi.c b/drivers/scsi/lpfc/lpfc_scsi.c
index 4e46045dea6d..c987c4fcdadc 100644
--- a/drivers/scsi/lpfc/lpfc_scsi.c
+++ b/drivers/scsi/lpfc/lpfc_scsi.c
@@ -542,6 +542,7 @@ lpfc_scsi_cmd_iocb_cmpl(struct lpfc_hba *phba, struct lpfc_iocbq *pIocbIn,
542 int result; 542 int result;
543 struct scsi_device *sdev, *tmp_sdev; 543 struct scsi_device *sdev, *tmp_sdev;
544 int depth = 0; 544 int depth = 0;
545 unsigned long flags;
545 546
546 lpfc_cmd->result = pIocbOut->iocb.un.ulpWord[4]; 547 lpfc_cmd->result = pIocbOut->iocb.un.ulpWord[4];
547 lpfc_cmd->status = pIocbOut->iocb.ulpStatus; 548 lpfc_cmd->status = pIocbOut->iocb.ulpStatus;
@@ -608,6 +609,15 @@ lpfc_scsi_cmd_iocb_cmpl(struct lpfc_hba *phba, struct lpfc_iocbq *pIocbIn,
608 cmd->scsi_done(cmd); 609 cmd->scsi_done(cmd);
609 610
610 if (phba->cfg_poll & ENABLE_FCP_RING_POLLING) { 611 if (phba->cfg_poll & ENABLE_FCP_RING_POLLING) {
612 /*
613 * If there is a thread waiting for command completion
614 * wake up the thread.
615 */
616 spin_lock_irqsave(sdev->host->host_lock, flags);
617 lpfc_cmd->pCmd = NULL;
618 if (lpfc_cmd->waitq)
619 wake_up(lpfc_cmd->waitq);
620 spin_unlock_irqrestore(sdev->host->host_lock, flags);
611 lpfc_release_scsi_buf(phba, lpfc_cmd); 621 lpfc_release_scsi_buf(phba, lpfc_cmd);
612 return; 622 return;
613 } 623 }
@@ -669,6 +679,16 @@ lpfc_scsi_cmd_iocb_cmpl(struct lpfc_hba *phba, struct lpfc_iocbq *pIocbIn,
669 } 679 }
670 } 680 }
671 681
682 /*
683 * If there is a thread waiting for command completion
684 * wake up the thread.
685 */
686 spin_lock_irqsave(sdev->host->host_lock, flags);
687 lpfc_cmd->pCmd = NULL;
688 if (lpfc_cmd->waitq)
689 wake_up(lpfc_cmd->waitq);
690 spin_unlock_irqrestore(sdev->host->host_lock, flags);
691
672 lpfc_release_scsi_buf(phba, lpfc_cmd); 692 lpfc_release_scsi_buf(phba, lpfc_cmd);
673} 693}
674 694
@@ -1018,8 +1038,8 @@ lpfc_abort_handler(struct scsi_cmnd *cmnd)
1018 struct lpfc_iocbq *abtsiocb; 1038 struct lpfc_iocbq *abtsiocb;
1019 struct lpfc_scsi_buf *lpfc_cmd; 1039 struct lpfc_scsi_buf *lpfc_cmd;
1020 IOCB_t *cmd, *icmd; 1040 IOCB_t *cmd, *icmd;
1021 unsigned int loop_count = 0;
1022 int ret = SUCCESS; 1041 int ret = SUCCESS;
1042 DECLARE_WAIT_QUEUE_HEAD_ONSTACK(waitq);
1023 1043
1024 lpfc_block_error_handler(cmnd); 1044 lpfc_block_error_handler(cmnd);
1025 lpfc_cmd = (struct lpfc_scsi_buf *)cmnd->host_scribble; 1045 lpfc_cmd = (struct lpfc_scsi_buf *)cmnd->host_scribble;
@@ -1074,17 +1094,15 @@ lpfc_abort_handler(struct scsi_cmnd *cmnd)
1074 if (phba->cfg_poll & DISABLE_FCP_RING_INT) 1094 if (phba->cfg_poll & DISABLE_FCP_RING_INT)
1075 lpfc_sli_poll_fcp_ring (phba); 1095 lpfc_sli_poll_fcp_ring (phba);
1076 1096
1097 lpfc_cmd->waitq = &waitq;
1077 /* Wait for abort to complete */ 1098 /* Wait for abort to complete */
1078 while (lpfc_cmd->pCmd == cmnd) 1099 wait_event_timeout(waitq,
1079 { 1100 (lpfc_cmd->pCmd != cmnd),
1080 if (phba->cfg_poll & DISABLE_FCP_RING_INT) 1101 (2*vport->cfg_devloss_tmo*HZ));
1081 lpfc_sli_poll_fcp_ring (phba);
1082 1102
1083 schedule_timeout_uninterruptible(LPFC_ABORT_WAIT * HZ); 1103 spin_lock_irq(shost->host_lock);
1084 if (++loop_count 1104 lpfc_cmd->waitq = NULL;
1085 > (2 * vport->cfg_devloss_tmo)/LPFC_ABORT_WAIT) 1105 spin_unlock_irq(shost->host_lock);
1086 break;
1087 }
1088 1106
1089 if (lpfc_cmd->pCmd == cmnd) { 1107 if (lpfc_cmd->pCmd == cmnd) {
1090 ret = FAILED; 1108 ret = FAILED;
diff --git a/drivers/scsi/lpfc/lpfc_scsi.h b/drivers/scsi/lpfc/lpfc_scsi.h
index 31787bb6d53e..daba92374985 100644
--- a/drivers/scsi/lpfc/lpfc_scsi.h
+++ b/drivers/scsi/lpfc/lpfc_scsi.h
@@ -138,6 +138,7 @@ struct lpfc_scsi_buf {
138 * Iotag is in here 138 * Iotag is in here
139 */ 139 */
140 struct lpfc_iocbq cur_iocbq; 140 struct lpfc_iocbq cur_iocbq;
141 wait_queue_head_t *waitq;
141}; 142};
142 143
143#define LPFC_SCSI_DMA_EXT_SIZE 264 144#define LPFC_SCSI_DMA_EXT_SIZE 264