summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTejun Heo <htejun@gmail.com>2006-11-14 22:37:35 +0900
committerJeff Garzik <jeff@garzik.org>2006-12-01 22:45:59 -0500
commit39599a5334decc2669ba794fb0ccd2b112ef1ba4 (patch)
treeff204f613472d673af4614e0bcef6689ea69c15a
parent61c0596c5fbef99df5518ae449be4ab49a2c2233 (diff)
downloadlinux-39599a5334decc2669ba794fb0ccd2b112ef1ba4.tar.bz2
[PATCH] libata: sync result_tf.flags w/ command tf.flags
libata didn't initialize result_tf.flags which indicates transfer type (RW/FUA) and address type (CHS/LBA/LBA48). ata_gen_fixed_sense() assumed result_tf.flags equals command tf.flags and failed to report the first failed block to SCSI layer because zero tf flags indicates CHS and bad block reporting for CHS is not implemented. Implement fill_result_tf() which sets result_tf.flags to command tf.flags and use it to fill result_tf. Signed-off-by: Tejun Heo <htejun@gmail.com> Signed-off-by: Jeff Garzik <jeff@garzik.org>
-rw-r--r--drivers/ata/libata-core.c14
1 files changed, 11 insertions, 3 deletions
diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c
index a52c07198839..13dcef809e5c 100644
--- a/drivers/ata/libata-core.c
+++ b/drivers/ata/libata-core.c
@@ -4536,6 +4536,14 @@ void __ata_qc_complete(struct ata_queued_cmd *qc)
qc->complete_fn(qc);
}
+static void fill_result_tf(struct ata_queued_cmd *qc)
+{
+ struct ata_port *ap = qc->ap;
+
+ ap->ops->tf_read(ap, &qc->result_tf);
+ qc->result_tf.flags = qc->tf.flags;
+}
+
/**
* ata_qc_complete - Complete an active ATA command
* @qc: Command to complete
@@ -4573,7 +4581,7 @@ void ata_qc_complete(struct ata_queued_cmd *qc)
if (unlikely(qc->flags & ATA_QCFLAG_FAILED)) {
if (!ata_tag_internal(qc->tag)) {
/* always fill result TF for failed qc */
- ap->ops->tf_read(ap, &qc->result_tf);
+ fill_result_tf(qc);
ata_qc_schedule_eh(qc);
return;
}
@@ -4581,7 +4589,7 @@ void ata_qc_complete(struct ata_queued_cmd *qc)
/* read result TF if requested */
if (qc->flags & ATA_QCFLAG_RESULT_TF)
- ap->ops->tf_read(ap, &qc->result_tf);
+ fill_result_tf(qc);
__ata_qc_complete(qc);
} else {
@@ -4590,7 +4598,7 @@ void ata_qc_complete(struct ata_queued_cmd *qc)
/* read result TF if failed or requested */
if (qc->err_mask || qc->flags & ATA_QCFLAG_RESULT_TF)
- ap->ops->tf_read(ap, &qc->result_tf);
+ fill_result_tf(qc);
__ata_qc_complete(qc);
}