diff options
Diffstat (limited to 'drivers/scsi/ahci.c')
-rw-r--r-- | drivers/scsi/ahci.c | 30 |
1 files changed, 19 insertions, 11 deletions
diff --git a/drivers/scsi/ahci.c b/drivers/scsi/ahci.c index 03829aedfd39..3df74a08fe22 100644 --- a/drivers/scsi/ahci.c +++ b/drivers/scsi/ahci.c | |||
@@ -312,8 +312,15 @@ static int ahci_port_start(struct ata_port *ap) | |||
312 | return -ENOMEM; | 312 | return -ENOMEM; |
313 | memset(pp, 0, sizeof(*pp)); | 313 | memset(pp, 0, sizeof(*pp)); |
314 | 314 | ||
315 | ap->pad = dma_alloc_coherent(dev, ATA_DMA_PAD_BUF_SZ, &ap->pad_dma, GFP_KERNEL); | ||
316 | if (!ap->pad) { | ||
317 | kfree(pp); | ||
318 | return -ENOMEM; | ||
319 | } | ||
320 | |||
315 | mem = dma_alloc_coherent(dev, AHCI_PORT_PRIV_DMA_SZ, &mem_dma, GFP_KERNEL); | 321 | mem = dma_alloc_coherent(dev, AHCI_PORT_PRIV_DMA_SZ, &mem_dma, GFP_KERNEL); |
316 | if (!mem) { | 322 | if (!mem) { |
323 | dma_free_coherent(dev, ATA_DMA_PAD_BUF_SZ, ap->pad, ap->pad_dma); | ||
317 | kfree(pp); | 324 | kfree(pp); |
318 | return -ENOMEM; | 325 | return -ENOMEM; |
319 | } | 326 | } |
@@ -389,6 +396,7 @@ static void ahci_port_stop(struct ata_port *ap) | |||
389 | ap->private_data = NULL; | 396 | ap->private_data = NULL; |
390 | dma_free_coherent(dev, AHCI_PORT_PRIV_DMA_SZ, | 397 | dma_free_coherent(dev, AHCI_PORT_PRIV_DMA_SZ, |
391 | pp->cmd_slot, pp->cmd_slot_dma); | 398 | pp->cmd_slot, pp->cmd_slot_dma); |
399 | dma_free_coherent(dev, ATA_DMA_PAD_BUF_SZ, ap->pad, ap->pad_dma); | ||
392 | kfree(pp); | 400 | kfree(pp); |
393 | } | 401 | } |
394 | 402 | ||
@@ -467,23 +475,23 @@ static void ahci_tf_read(struct ata_port *ap, struct ata_taskfile *tf) | |||
467 | static void ahci_fill_sg(struct ata_queued_cmd *qc) | 475 | static void ahci_fill_sg(struct ata_queued_cmd *qc) |
468 | { | 476 | { |
469 | struct ahci_port_priv *pp = qc->ap->private_data; | 477 | struct ahci_port_priv *pp = qc->ap->private_data; |
470 | unsigned int i; | 478 | struct scatterlist *sg; |
479 | struct ahci_sg *ahci_sg; | ||
471 | 480 | ||
472 | VPRINTK("ENTER\n"); | 481 | VPRINTK("ENTER\n"); |
473 | 482 | ||
474 | /* | 483 | /* |
475 | * Next, the S/G list. | 484 | * Next, the S/G list. |
476 | */ | 485 | */ |
477 | for (i = 0; i < qc->n_elem; i++) { | 486 | ahci_sg = pp->cmd_tbl_sg; |
478 | u32 sg_len; | 487 | ata_for_each_sg(sg, qc) { |
479 | dma_addr_t addr; | 488 | dma_addr_t addr = sg_dma_address(sg); |
480 | 489 | u32 sg_len = sg_dma_len(sg); | |
481 | addr = sg_dma_address(&qc->sg[i]); | 490 | |
482 | sg_len = sg_dma_len(&qc->sg[i]); | 491 | ahci_sg->addr = cpu_to_le32(addr & 0xffffffff); |
483 | 492 | ahci_sg->addr_hi = cpu_to_le32((addr >> 16) >> 16); | |
484 | pp->cmd_tbl_sg[i].addr = cpu_to_le32(addr & 0xffffffff); | 493 | ahci_sg->flags_size = cpu_to_le32(sg_len - 1); |
485 | pp->cmd_tbl_sg[i].addr_hi = cpu_to_le32((addr >> 16) >> 16); | 494 | ahci_sg++; |
486 | pp->cmd_tbl_sg[i].flags_size = cpu_to_le32(sg_len - 1); | ||
487 | } | 495 | } |
488 | } | 496 | } |
489 | 497 | ||