diff options
author | Tejun Heo <htejun@gmail.com> | 2007-12-05 02:43:07 -0500 |
---|---|---|
committer | Jeff Garzik <jeff@garzik.org> | 2008-01-23 05:24:14 -0500 |
commit | 55dba3120fbcbea6800f9a18503d25f73212a347 (patch) | |
tree | 1b23e606aad8bc58dbe68ca905c0658625fb176e /drivers/ata/pata_bf54x.c | |
parent | ceb0c642624f634c5b4f46b0e22df19be87a2e53 (diff) |
libata: update ->data_xfer hook for ATAPI
Depending on how many bytes are transferred as a unit, PIO data
transfer may consume more bytes than requested. Knowing how much
data is consumed is necessary to determine how much is left for
draining. This patch update ->data_xfer such that it returns the
number of consumed bytes.
While at it, it also makes the following changes.
* s/adev/dev/
* use READ/WRITE constants for rw indication
* misc clean ups
Signed-off-by: Tejun Heo <htejun@gmail.com>
Signed-off-by: Jeff Garzik <jeff@garzik.org>
Diffstat (limited to 'drivers/ata/pata_bf54x.c')
-rw-r--r-- | drivers/ata/pata_bf54x.c | 28 |
1 files changed, 15 insertions, 13 deletions
diff --git a/drivers/ata/pata_bf54x.c b/drivers/ata/pata_bf54x.c index 7842cc487359..41cd921082ba 100644 --- a/drivers/ata/pata_bf54x.c +++ b/drivers/ata/pata_bf54x.c | |||
@@ -1167,34 +1167,36 @@ static unsigned char bfin_bmdma_status(struct ata_port *ap) | |||
1167 | * Note: Original code is ata_data_xfer(). | 1167 | * Note: Original code is ata_data_xfer(). |
1168 | */ | 1168 | */ |
1169 | 1169 | ||
1170 | static void bfin_data_xfer(struct ata_device *adev, unsigned char *buf, | 1170 | static unsigned int bfin_data_xfer(struct ata_device *dev, unsigned char *buf, |
1171 | unsigned int buflen, int write_data) | 1171 | unsigned int buflen, int rw) |
1172 | { | 1172 | { |
1173 | struct ata_port *ap = adev->link->ap; | 1173 | struct ata_port *ap = dev->link->ap; |
1174 | unsigned int words = buflen >> 1; | ||
1175 | unsigned short *buf16 = (u16 *) buf; | ||
1176 | void __iomem *base = (void __iomem *)ap->ioaddr.ctl_addr; | 1174 | void __iomem *base = (void __iomem *)ap->ioaddr.ctl_addr; |
1175 | unsigned int words = buflen >> 1; | ||
1176 | unsigned short *buf16 = (u16 *)buf; | ||
1177 | 1177 | ||
1178 | /* Transfer multiple of 2 bytes */ | 1178 | /* Transfer multiple of 2 bytes */ |
1179 | if (write_data) { | 1179 | if (rw == READ) |
1180 | write_atapi_data(base, words, buf16); | ||
1181 | } else { | ||
1182 | read_atapi_data(base, words, buf16); | 1180 | read_atapi_data(base, words, buf16); |
1183 | } | 1181 | else |
1182 | write_atapi_data(base, words, buf16); | ||
1184 | 1183 | ||
1185 | /* Transfer trailing 1 byte, if any. */ | 1184 | /* Transfer trailing 1 byte, if any. */ |
1186 | if (unlikely(buflen & 0x01)) { | 1185 | if (unlikely(buflen & 0x01)) { |
1187 | unsigned short align_buf[1] = { 0 }; | 1186 | unsigned short align_buf[1] = { 0 }; |
1188 | unsigned char *trailing_buf = buf + buflen - 1; | 1187 | unsigned char *trailing_buf = buf + buflen - 1; |
1189 | 1188 | ||
1190 | if (write_data) { | 1189 | if (rw == READ) { |
1191 | memcpy(align_buf, trailing_buf, 1); | ||
1192 | write_atapi_data(base, 1, align_buf); | ||
1193 | } else { | ||
1194 | read_atapi_data(base, 1, align_buf); | 1190 | read_atapi_data(base, 1, align_buf); |
1195 | memcpy(trailing_buf, align_buf, 1); | 1191 | memcpy(trailing_buf, align_buf, 1); |
1192 | } else { | ||
1193 | memcpy(align_buf, trailing_buf, 1); | ||
1194 | write_atapi_data(base, 1, align_buf); | ||
1196 | } | 1195 | } |
1196 | words++; | ||
1197 | } | 1197 | } |
1198 | |||
1199 | return words << 1; | ||
1198 | } | 1200 | } |
1199 | 1201 | ||
1200 | /** | 1202 | /** |