diff options
author | Tejun Heo <htejun@gmail.com> | 2006-11-14 08:37:35 -0500 |
---|---|---|
committer | Jeff Garzik <jeff@garzik.org> | 2006-12-01 22:46:00 -0500 |
commit | 35b649fe2587b2e569c17c022ba3506ba441b6a2 (patch) | |
tree | 07d1b36f0241d48fa71159e7bc7a096ac5842bed /drivers/ata | |
parent | 750426aa1ad1ddd1fa8bb4ed531a7956f3b9a27c (diff) |
[PATCH] libata: implement ata_tf_read_block()
Implement ata_tf_read_block().
Signed-off-by: Tejun Heo <htejun@gmail.com>
Signed-off-by: Jeff Garzik <jeff@garzik.org>
Diffstat (limited to 'drivers/ata')
-rw-r--r-- | drivers/ata/libata-core.c | 43 | ||||
-rw-r--r-- | drivers/ata/libata.h | 1 |
2 files changed, 44 insertions, 0 deletions
diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c index 13dcef809e5c..3fd7c7932707 100644 --- a/drivers/ata/libata-core.c +++ b/drivers/ata/libata-core.c | |||
@@ -240,6 +240,49 @@ int ata_rwcmd_protocol(struct ata_queued_cmd *qc) | |||
240 | } | 240 | } |
241 | 241 | ||
242 | /** | 242 | /** |
243 | * ata_tf_read_block - Read block address from ATA taskfile | ||
244 | * @tf: ATA taskfile of interest | ||
245 | * @dev: ATA device @tf belongs to | ||
246 | * | ||
247 | * LOCKING: | ||
248 | * None. | ||
249 | * | ||
250 | * Read block address from @tf. This function can handle all | ||
251 | * three address formats - LBA, LBA48 and CHS. tf->protocol and | ||
252 | * flags select the address format to use. | ||
253 | * | ||
254 | * RETURNS: | ||
255 | * Block address read from @tf. | ||
256 | */ | ||
257 | u64 ata_tf_read_block(struct ata_taskfile *tf, struct ata_device *dev) | ||
258 | { | ||
259 | u64 block = 0; | ||
260 | |||
261 | if (tf->flags & ATA_TFLAG_LBA) { | ||
262 | if (tf->flags & ATA_TFLAG_LBA48) { | ||
263 | block |= (u64)tf->hob_lbah << 40; | ||
264 | block |= (u64)tf->hob_lbam << 32; | ||
265 | block |= tf->hob_lbal << 24; | ||
266 | } else | ||
267 | block |= (tf->device & 0xf) << 24; | ||
268 | |||
269 | block |= tf->lbah << 16; | ||
270 | block |= tf->lbam << 8; | ||
271 | block |= tf->lbal; | ||
272 | } else { | ||
273 | u32 cyl, head, sect; | ||
274 | |||
275 | cyl = tf->lbam | (tf->lbah << 8); | ||
276 | head = tf->device & 0xf; | ||
277 | sect = tf->lbal; | ||
278 | |||
279 | block = (cyl * dev->heads + head) * dev->sectors + sect; | ||
280 | } | ||
281 | |||
282 | return block; | ||
283 | } | ||
284 | |||
285 | /** | ||
243 | * ata_pack_xfermask - Pack pio, mwdma and udma masks into xfer_mask | 286 | * ata_pack_xfermask - Pack pio, mwdma and udma masks into xfer_mask |
244 | * @pio_mask: pio_mask | 287 | * @pio_mask: pio_mask |
245 | * @mwdma_mask: mwdma_mask | 288 | * @mwdma_mask: mwdma_mask |
diff --git a/drivers/ata/libata.h b/drivers/ata/libata.h index be2ac39f013b..2d532da8c398 100644 --- a/drivers/ata/libata.h +++ b/drivers/ata/libata.h | |||
@@ -52,6 +52,7 @@ extern int atapi_dmadir; | |||
52 | extern int libata_fua; | 52 | extern int libata_fua; |
53 | extern struct ata_queued_cmd *ata_qc_new_init(struct ata_device *dev); | 53 | extern struct ata_queued_cmd *ata_qc_new_init(struct ata_device *dev); |
54 | extern int ata_rwcmd_protocol(struct ata_queued_cmd *qc); | 54 | extern int ata_rwcmd_protocol(struct ata_queued_cmd *qc); |
55 | extern u64 ata_tf_read_block(struct ata_taskfile *tf, struct ata_device *dev); | ||
55 | extern void ata_dev_disable(struct ata_device *dev); | 56 | extern void ata_dev_disable(struct ata_device *dev); |
56 | extern void ata_port_flush_task(struct ata_port *ap); | 57 | extern void ata_port_flush_task(struct ata_port *ap); |
57 | extern unsigned ata_exec_internal(struct ata_device *dev, | 58 | extern unsigned ata_exec_internal(struct ata_device *dev, |