diff options
author | David C Somayajulu <david.somayajulu@qlogic.com> | 2008-03-19 14:23:03 -0400 |
---|---|---|
committer | James Bottomley <James.Bottomley@HansenPartnership.com> | 2008-04-07 13:19:00 -0400 |
commit | 9d56291366cd6ab156be722e42cf487bef20f5fd (patch) | |
tree | d85fadb003a7ed4a3ac8380487423a2b6ce31bb2 /drivers/scsi/qla4xxx/ql4_isr.c | |
parent | af7a5647c03c18f5ea58033710ccb23d71727e0c (diff) |
[SCSI] qla4xxx: fix scsi command completion, lun reset and target reset code
This patch contains the following:
1. when hba completion status is good, check for iscsi transport
errors (underflow/overflow) prior to checking the scsi status
2. New firmware requires that one marker iocb be issued for each task
management command. The patch issues marker iocb immediately
following a LUN or Target reset.
Signed-off-by: David C Somayajulu <david.somayajulu@qlogic.com>
Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
Diffstat (limited to 'drivers/scsi/qla4xxx/ql4_isr.c')
-rw-r--r-- | drivers/scsi/qla4xxx/ql4_isr.c | 40 |
1 files changed, 5 insertions, 35 deletions
diff --git a/drivers/scsi/qla4xxx/ql4_isr.c b/drivers/scsi/qla4xxx/ql4_isr.c index fc84db4069f4..a91a57c57bff 100644 --- a/drivers/scsi/qla4xxx/ql4_isr.c +++ b/drivers/scsi/qla4xxx/ql4_isr.c | |||
@@ -11,28 +11,6 @@ | |||
11 | #include "ql4_inline.h" | 11 | #include "ql4_inline.h" |
12 | 12 | ||
13 | /** | 13 | /** |
14 | * qla2x00_process_completed_request() - Process a Fast Post response. | ||
15 | * @ha: SCSI driver HA context | ||
16 | * @index: SRB index | ||
17 | **/ | ||
18 | static void qla4xxx_process_completed_request(struct scsi_qla_host *ha, | ||
19 | uint32_t index) | ||
20 | { | ||
21 | struct srb *srb; | ||
22 | |||
23 | srb = qla4xxx_del_from_active_array(ha, index); | ||
24 | if (srb) { | ||
25 | /* Save ISP completion status */ | ||
26 | srb->cmd->result = DID_OK << 16; | ||
27 | qla4xxx_srb_compl(ha, srb); | ||
28 | } else { | ||
29 | DEBUG2(printk("scsi%ld: Invalid ISP SCSI completion handle = " | ||
30 | "%d\n", ha->host_no, index)); | ||
31 | set_bit(DPC_RESET_HA, &ha->dpc_flags); | ||
32 | } | ||
33 | } | ||
34 | |||
35 | /** | ||
36 | * qla4xxx_status_entry - processes status IOCBs | 14 | * qla4xxx_status_entry - processes status IOCBs |
37 | * @ha: Pointer to host adapter structure. | 15 | * @ha: Pointer to host adapter structure. |
38 | * @sts_entry: Pointer to status entry structure. | 16 | * @sts_entry: Pointer to status entry structure. |
@@ -47,14 +25,6 @@ static void qla4xxx_status_entry(struct scsi_qla_host *ha, | |||
47 | uint32_t residual; | 25 | uint32_t residual; |
48 | uint16_t sensebytecnt; | 26 | uint16_t sensebytecnt; |
49 | 27 | ||
50 | if (sts_entry->completionStatus == SCS_COMPLETE && | ||
51 | sts_entry->scsiStatus == 0) { | ||
52 | qla4xxx_process_completed_request(ha, | ||
53 | le32_to_cpu(sts_entry-> | ||
54 | handle)); | ||
55 | return; | ||
56 | } | ||
57 | |||
58 | srb = qla4xxx_del_from_active_array(ha, le32_to_cpu(sts_entry->handle)); | 28 | srb = qla4xxx_del_from_active_array(ha, le32_to_cpu(sts_entry->handle)); |
59 | if (!srb) { | 29 | if (!srb) { |
60 | /* FIXMEdg: Don't we need to reset ISP in this case??? */ | 30 | /* FIXMEdg: Don't we need to reset ISP in this case??? */ |
@@ -62,6 +32,9 @@ static void qla4xxx_status_entry(struct scsi_qla_host *ha, | |||
62 | "handle 0x%x, sp=%p. This cmd may have already " | 32 | "handle 0x%x, sp=%p. This cmd may have already " |
63 | "been completed.\n", ha->host_no, __func__, | 33 | "been completed.\n", ha->host_no, __func__, |
64 | le32_to_cpu(sts_entry->handle), srb)); | 34 | le32_to_cpu(sts_entry->handle), srb)); |
35 | dev_warn(&ha->pdev->dev, "%s invalid status entry:" | ||
36 | " handle=0x%0x\n", __func__, sts_entry->handle); | ||
37 | set_bit(DPC_RESET_HA, &ha->dpc_flags); | ||
65 | return; | 38 | return; |
66 | } | 39 | } |
67 | 40 | ||
@@ -88,10 +61,6 @@ static void qla4xxx_status_entry(struct scsi_qla_host *ha, | |||
88 | scsi_status = sts_entry->scsiStatus; | 61 | scsi_status = sts_entry->scsiStatus; |
89 | switch (sts_entry->completionStatus) { | 62 | switch (sts_entry->completionStatus) { |
90 | case SCS_COMPLETE: | 63 | case SCS_COMPLETE: |
91 | if (scsi_status == 0) { | ||
92 | cmd->result = DID_OK << 16; | ||
93 | break; | ||
94 | } | ||
95 | 64 | ||
96 | if (sts_entry->iscsiFlags & ISCSI_FLAG_RESIDUAL_OVER) { | 65 | if (sts_entry->iscsiFlags & ISCSI_FLAG_RESIDUAL_OVER) { |
97 | cmd->result = DID_ERROR << 16; | 66 | cmd->result = DID_ERROR << 16; |
@@ -100,7 +69,8 @@ static void qla4xxx_status_entry(struct scsi_qla_host *ha, | |||
100 | 69 | ||
101 | if (sts_entry->iscsiFlags &ISCSI_FLAG_RESIDUAL_UNDER) { | 70 | if (sts_entry->iscsiFlags &ISCSI_FLAG_RESIDUAL_UNDER) { |
102 | scsi_set_resid(cmd, residual); | 71 | scsi_set_resid(cmd, residual); |
103 | if ((scsi_bufflen(cmd) - residual) < cmd->underflow) { | 72 | if (!scsi_status && ((scsi_bufflen(cmd) - residual) < |
73 | cmd->underflow)) { | ||
104 | 74 | ||
105 | cmd->result = DID_ERROR << 16; | 75 | cmd->result = DID_ERROR << 16; |
106 | 76 | ||