libata: add qc_fill_rtf port operation
authorTejun Heo <htejun@gmail.com>
Mon, 7 Apr 2008 13:47:20 +0000 (22:47 +0900)
committerJeff Garzik <jgarzik@redhat.com>
Thu, 17 Apr 2008 19:44:23 +0000 (15:44 -0400)
On command completion, ata_qc_complete() directly called ops->tf_read
to fill qc->result_tf.  This patch adds ops->qc_fill_rtf to replace
hardcoded ops->tf_read usage.

ata_sff_qc_fill_rtf() which uses ops->tf_read to fill result_tf is
implemented and set in ata_base_port_ops and other ops tables which
don't inherit from ata_base_port_ops, so this patch doesn't introduce
any behavior change.

ops->qc_fill_rtf() is similar to ops->sff_tf_read() but can only be
called when a command finishes.  As some non-SFF controllers don't
have TF registers defined unless they're associated with in-flight
commands, this limited operation makes life easier for those drivers
and help lifting SFF assumptions from libata core layer.

Signed-off-by: Tejun Heo <htejun@gmail.com>
drivers/ata/libata-core.c
drivers/ata/libata-sff.c
drivers/ata/sata_sx4.c
drivers/scsi/ipr.c
drivers/scsi/libsas/sas_ata.c
include/linux/libata.h

index 51876b93c1b73f926b51cb61a3fc6fbc478b15e8..3b822124e97e1a977f280ae52b0da476d3de97a9 100644 (file)
@@ -74,6 +74,7 @@ const unsigned long sata_deb_timing_hotplug[]         = {  25,  500, 2000 };
 const unsigned long sata_deb_timing_long[]             = { 100, 2000, 5000 };
 
 const struct ata_port_operations ata_base_port_ops = {
+       .qc_fill_rtf            = ata_sff_qc_fill_rtf,
        .prereset               = ata_std_prereset,
        .postreset              = ata_std_postreset,
        .error_handler          = ata_std_error_handler,
@@ -4562,7 +4563,7 @@ static void fill_result_tf(struct ata_queued_cmd *qc)
        struct ata_port *ap = qc->ap;
 
        qc->result_tf.flags = qc->tf.flags;
-       ap->ops->sff_tf_read(ap, &qc->result_tf);
+       ap->ops->qc_fill_rtf(qc);
 }
 
 static void ata_verify_xfer(struct ata_queued_cmd *qc)
index 5be8a6058dacbbd58098ebb1c2f64136b223d7d8..5ae813f54420629d960ed5aa53814948e3745c7e 100644 (file)
@@ -1407,6 +1407,25 @@ unsigned int ata_sff_qc_issue(struct ata_queued_cmd *qc)
        return 0;
 }
 
+/**
+ *     ata_sff_qc_fill_rtf - fill result TF using ->sff_tf_read
+ *     @qc: qc to fill result TF for
+ *
+ *     @qc is finished and result TF needs to be filled.  Fill it
+ *     using ->sff_tf_read.
+ *
+ *     LOCKING:
+ *     spin_lock_irqsave(host lock)
+ *
+ *     RETURNS:
+ *     true indicating that result TF is successfully filled.
+ */
+bool ata_sff_qc_fill_rtf(struct ata_queued_cmd *qc)
+{
+       qc->ap->ops->sff_tf_read(qc->ap, &qc->result_tf);
+       return true;
+}
+
 /**
  *     ata_sff_host_intr - Handle host interrupt for given (port, task)
  *     @ap: Port on which interrupt arrived (possibly...)
@@ -2724,6 +2743,7 @@ EXPORT_SYMBOL_GPL(ata_sff_irq_on);
 EXPORT_SYMBOL_GPL(ata_sff_irq_clear);
 EXPORT_SYMBOL_GPL(ata_sff_hsm_move);
 EXPORT_SYMBOL_GPL(ata_sff_qc_issue);
+EXPORT_SYMBOL_GPL(ata_sff_qc_fill_rtf);
 EXPORT_SYMBOL_GPL(ata_sff_host_intr);
 EXPORT_SYMBOL_GPL(ata_sff_interrupt);
 EXPORT_SYMBOL_GPL(ata_sff_freeze);
index 6107eff731f3633a63eb72421854d1265726b3e0..ec04b8d3c791ecc3e0c544aa2d4b05f34b9923a7 100644 (file)
@@ -251,6 +251,7 @@ static struct ata_port_operations pdc_20621_ops = {
        .phy_reset              = pdc_20621_phy_reset,
        .qc_prep                = pdc20621_qc_prep,
        .qc_issue               = pdc20621_qc_issue,
+       .qc_fill_rtf            = ata_sff_qc_fill_rtf,
        .sff_data_xfer          = ata_sff_data_xfer,
        .eng_timeout            = pdc_eng_timeout,
        .sff_irq_clear          = pdc20621_irq_clear,
index 5bddae19d1fb8df5f90d009694ca040302dd94e7..2ecd3299152226e41db26c532d0b016af946ded6 100644 (file)
@@ -5280,6 +5280,7 @@ static struct ata_port_operations ipr_sata_ops = {
        .sff_tf_read = ipr_tf_read,
        .qc_prep = ata_noop_qc_prep,
        .qc_issue = ipr_qc_issue,
+       .qc_fill_rtf = ata_sff_qc_fill_rtf,
        .port_start = ata_sas_port_start,
        .port_stop = ata_sas_port_stop
 };
index a1664b87927ac13541b9146ec344f81028e149fc..2ec255839dcd6129c6875f0acef5a01cfc8a9a89 100644 (file)
@@ -356,6 +356,7 @@ static struct ata_port_operations sas_sata_ops = {
        .sff_tf_read            = sas_ata_tf_read,
        .qc_prep                = ata_noop_qc_prep,
        .qc_issue               = sas_ata_qc_issue,
+       .qc_fill_rtf            = ata_sff_qc_fill_rtf,
        .port_start             = ata_sas_port_start,
        .port_stop              = ata_sas_port_stop,
        .scr_read               = sas_ata_scr_read,
index 2b5a0b77e179a72a64b0a800ba9955e39cca71ab..bb4200d42f0d778fba8fb34802b02ac2f56068a8 100644 (file)
@@ -715,6 +715,7 @@ struct ata_port_operations {
        int  (*check_atapi_dma)(struct ata_queued_cmd *qc);
        void (*qc_prep)(struct ata_queued_cmd *qc);
        unsigned int (*qc_issue)(struct ata_queued_cmd *qc);
+       bool (*qc_fill_rtf)(struct ata_queued_cmd *qc);
 
        /*
         * Configuration and exception handling
@@ -1385,6 +1386,7 @@ extern void ata_sff_irq_clear(struct ata_port *ap);
 extern int ata_sff_hsm_move(struct ata_port *ap, struct ata_queued_cmd *qc,
                            u8 status, int in_wq);
 extern unsigned int ata_sff_qc_issue(struct ata_queued_cmd *qc);
+extern bool ata_sff_qc_fill_rtf(struct ata_queued_cmd *qc);
 extern unsigned int ata_sff_host_intr(struct ata_port *ap,
                                      struct ata_queued_cmd *qc);
 extern irqreturn_t ata_sff_interrupt(int irq, void *dev_instance);