summaryrefslogtreecommitdiffstats
path: root/drivers/ata/libata-sff.c
diff options
context:
space:
mode:
authorAkira Iguchi <akira2.iguchi@toshiba.co.jp>2007-01-26 16:27:32 +0900
committerJeff Garzik <jeff@garzik.org>2007-02-09 17:39:38 -0500
commit836250069fc0eeebe8b6aed772281535cc6e34f9 (patch)
tree73c886ae7fd75dd2c9b5b17e11ea3b6b76b42fed /drivers/ata/libata-sff.c
parent7f25377043925554cb9f3f9d8ada3390f71a5d10 (diff)
downloadlinux-836250069fc0eeebe8b6aed772281535cc6e34f9.tar.bz2
libata: add another IRQ calls (core and headers)
This patch is against the libata core and headers. Two IRQ calls are added in ata_port_operations. - irq_on() is used to enable interrupts. - irq_ack() is used to acknowledge a device interrupt. In most drivers, ata_irq_on() and ata_irq_ack() are used for irq_on and irq_ack respectively. In some drivers (ex: ahci, sata_sil24) which cannot use them as is, ata_dummy_irq_on() and ata_dummy_irq_ack() are used. Signed-off-by: Kou Ishizaki <kou.ishizaki@toshiba.co.jp> Signed-off-by: Akira Iguchi <akira2.iguchi@toshiba.co.jp> Signed-off-by: Jeff Garzik <jeff@garzik.org>
Diffstat (limited to 'drivers/ata/libata-sff.c')
-rw-r--r--drivers/ata/libata-sff.c43
1 files changed, 41 insertions, 2 deletions
diff --git a/drivers/ata/libata-sff.c b/drivers/ata/libata-sff.c
index c561b3be4a97..16bc3e35bdd4 100644
--- a/drivers/ata/libata-sff.c
+++ b/drivers/ata/libata-sff.c
@@ -64,6 +64,46 @@ u8 ata_irq_on(struct ata_port *ap)
return tmp;
}
+u8 ata_dummy_irq_on (struct ata_port *ap) { return 0; }
+
+/**
+ * ata_irq_ack - Acknowledge a device interrupt.
+ * @ap: Port on which interrupts are enabled.
+ *
+ * Wait up to 10 ms for legacy IDE device to become idle (BUSY
+ * or BUSY+DRQ clear). Obtain dma status and port status from
+ * device. Clear the interrupt. Return port status.
+ *
+ * LOCKING:
+ */
+
+u8 ata_irq_ack(struct ata_port *ap, unsigned int chk_drq)
+{
+ unsigned int bits = chk_drq ? ATA_BUSY | ATA_DRQ : ATA_BUSY;
+ u8 host_stat, post_stat, status;
+
+ status = ata_busy_wait(ap, bits, 1000);
+ if (status & bits)
+ if (ata_msg_err(ap))
+ printk(KERN_ERR "abnormal status 0x%X\n", status);
+
+ /* get controller status; clear intr, err bits */
+ host_stat = ioread8(ap->ioaddr.bmdma_addr + ATA_DMA_STATUS);
+ iowrite8(host_stat | ATA_DMA_INTR | ATA_DMA_ERR,
+ ap->ioaddr.bmdma_addr + ATA_DMA_STATUS);
+
+ post_stat = ioread8(ap->ioaddr.bmdma_addr + ATA_DMA_STATUS);
+
+ if (ata_msg_intr(ap))
+ printk(KERN_INFO "%s: irq ack: host_stat 0x%X, new host_stat 0x%X, drv_stat 0x%X\n",
+ __FUNCTION__,
+ host_stat, post_stat, status);
+
+ return status;
+}
+
+u8 ata_dummy_irq_ack(struct ata_port *ap, unsigned int chk_drq) { return 0; }
+
/**
* ata_tf_load - send taskfile registers to host controller
* @ap: Port to which output is sent
@@ -370,8 +410,7 @@ void ata_bmdma_thaw(struct ata_port *ap)
/* clear & re-enable interrupts */
ata_chk_status(ap);
ap->ops->irq_clear(ap);
- if (ap->ioaddr.ctl_addr) /* FIXME: hack. create a hook instead */
- ata_irq_on(ap);
+ ap->ops->irq_on(ap);
}
/**