aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/libata-scsi.c
diff options
context:
space:
mode:
authorJeff Garzik <jgarzik@pobox.com>2005-10-05 15:02:14 -0400
committerJeff Garzik <jgarzik@pobox.com>2005-10-05 15:02:14 -0400
commita15dbeb4772626a015337dea06da67095aec3862 (patch)
tree2834c0f61b396c2eba008c176b49460c02a564f5 /drivers/scsi/libata-scsi.c
parent67846b30171cc4d706125f630193a76a26bb334a (diff)
downloadkernel_samsung_smdk4412-a15dbeb4772626a015337dea06da67095aec3862.tar.gz
kernel_samsung_smdk4412-a15dbeb4772626a015337dea06da67095aec3862.tar.bz2
kernel_samsung_smdk4412-a15dbeb4772626a015337dea06da67095aec3862.zip
libata: ATAPI command completion tweaks and notes
1) note urgent bug, that completes command twice 2) only fix up INQUIRY data if the SCSI version is zero (typically indicates ATAPI MMC-ish device) 3) if there is a problem on the ATA bus, don't bother with REQUEST SENSE, just directly handle the error based on Status/Error registers.
Diffstat (limited to 'drivers/scsi/libata-scsi.c')
-rw-r--r--drivers/scsi/libata-scsi.c31
1 files changed, 28 insertions, 3 deletions
diff --git a/drivers/scsi/libata-scsi.c b/drivers/scsi/libata-scsi.c
index 45ebe9fd52e..1a1ef3429e5 100644
--- a/drivers/scsi/libata-scsi.c
+++ b/drivers/scsi/libata-scsi.c
@@ -1483,9 +1483,18 @@ static int atapi_qc_complete(struct ata_queued_cmd *qc, u8 drv_stat)
{
struct scsi_cmnd *cmd = qc->scsicmd;
- if (unlikely(drv_stat & (ATA_ERR | ATA_BUSY | ATA_DRQ))) {
+ if (unlikely(drv_stat & (ATA_BUSY | ATA_DRQ)))
+ ata_to_sense_error(qc, drv_stat);
+ else if (unlikely(drv_stat & ATA_ERR)) {
DPRINTK("request check condition\n");
+ /* FIXME: command completion with check condition
+ * but no sense causes the error handler to run,
+ * which then issues REQUEST SENSE, fills in the sense
+ * buffer, and completes the command (for the second
+ * time). We need to issue REQUEST SENSE some other
+ * way, to avoid completing the command twice.
+ */
cmd->result = SAM_STAT_CHECK_CONDITION;
qc->scsidone(cmd);
@@ -1499,10 +1508,26 @@ static int atapi_qc_complete(struct ata_queued_cmd *qc, u8 drv_stat)
unsigned int buflen;
buflen = ata_scsi_rbuf_get(cmd, &buf);
- buf[2] = 0x5;
- buf[3] = (buf[3] & 0xf0) | 2;
+
+ /* ATAPI devices typically report zero for their SCSI version,
+ * and sometimes deviate from the spec WRT response data
+ * format. If SCSI version is reported as zero like normal,
+ * then we make the following fixups: 1) Fake MMC-5 version,
+ * to indicate to the Linux scsi midlayer this is a modern
+ * device. 2) Ensure response data format / ATAPI information
+ * are always correct.
+ */
+ /* FIXME: do we ever override EVPD pages and the like, with
+ * this code?
+ */
+ if (buf[2] == 0) {
+ buf[2] = 0x5;
+ buf[3] = 0x32;
+ }
+
ata_scsi_rbuf_put(cmd, buf);
}
+
cmd->result = SAM_STAT_GOOD;
}