diff options
author | Nicolas Ferre <nicolas.ferre@atmel.com> | 2009-12-14 21:01:30 -0500 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2009-12-15 11:53:35 -0500 |
commit | 2635d1ba711560d521f6218c585a3e0401f566e1 (patch) | |
tree | 11c8f09f15cd2f19bfd6f2d2d9b2cac67544179f /drivers/mmc | |
parent | bd68e0838fe85794b06892054772fa013a8d1986 (diff) |
atmel-mci: change use of dma slave interface
Allow the use of another DMA controller driver in atmel-mci sd/mmc driver.
This adds a generic dma_slave pointer to the mci platform structure where
we can store DMA controller information. In atmel-mci we use information
provided by this structure to initialize the driver (with new helper
functions that are architecture dependant).
This also adds at32/avr32 chip modifications to cope with this new access
method.
Signed-off-by: Nicolas Ferre <nicolas.ferre@atmel.com>
Cc: Haavard Skinnemoen <hskinnemoen@atmel.com>
Cc: <linux-mmc@vger.kernel.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'drivers/mmc')
-rw-r--r-- | drivers/mmc/host/atmel-mci.c | 56 |
1 files changed, 36 insertions, 20 deletions
diff --git a/drivers/mmc/host/atmel-mci.c b/drivers/mmc/host/atmel-mci.c index fc25586b7ee1..ba8b219d44c1 100644 --- a/drivers/mmc/host/atmel-mci.c +++ b/drivers/mmc/host/atmel-mci.c | |||
@@ -25,6 +25,8 @@ | |||
25 | #include <linux/stat.h> | 25 | #include <linux/stat.h> |
26 | 26 | ||
27 | #include <linux/mmc/host.h> | 27 | #include <linux/mmc/host.h> |
28 | |||
29 | #include <mach/atmel-mci.h> | ||
28 | #include <linux/atmel-mci.h> | 30 | #include <linux/atmel-mci.h> |
29 | 31 | ||
30 | #include <asm/io.h> | 32 | #include <asm/io.h> |
@@ -1584,14 +1586,43 @@ static void __exit atmci_cleanup_slot(struct atmel_mci_slot *slot, | |||
1584 | #ifdef CONFIG_MMC_ATMELMCI_DMA | 1586 | #ifdef CONFIG_MMC_ATMELMCI_DMA |
1585 | static bool filter(struct dma_chan *chan, void *slave) | 1587 | static bool filter(struct dma_chan *chan, void *slave) |
1586 | { | 1588 | { |
1587 | struct dw_dma_slave *dws = slave; | 1589 | struct mci_dma_data *sl = slave; |
1588 | 1590 | ||
1589 | if (dws->dma_dev == chan->device->dev) { | 1591 | if (sl && find_slave_dev(sl) == chan->device->dev) { |
1590 | chan->private = dws; | 1592 | chan->private = slave_data_ptr(sl); |
1591 | return true; | 1593 | return true; |
1592 | } else | 1594 | } else { |
1593 | return false; | 1595 | return false; |
1596 | } | ||
1594 | } | 1597 | } |
1598 | |||
1599 | static void atmci_configure_dma(struct atmel_mci *host) | ||
1600 | { | ||
1601 | struct mci_platform_data *pdata; | ||
1602 | |||
1603 | if (host == NULL) | ||
1604 | return; | ||
1605 | |||
1606 | pdata = host->pdev->dev.platform_data; | ||
1607 | |||
1608 | if (pdata && find_slave_dev(pdata->dma_slave)) { | ||
1609 | dma_cap_mask_t mask; | ||
1610 | |||
1611 | setup_dma_addr(pdata->dma_slave, | ||
1612 | host->mapbase + MCI_TDR, | ||
1613 | host->mapbase + MCI_RDR); | ||
1614 | |||
1615 | /* Try to grab a DMA channel */ | ||
1616 | dma_cap_zero(mask); | ||
1617 | dma_cap_set(DMA_SLAVE, mask); | ||
1618 | host->dma.chan = | ||
1619 | dma_request_channel(mask, filter, pdata->dma_slave); | ||
1620 | } | ||
1621 | if (!host->dma.chan) | ||
1622 | dev_notice(&host->pdev->dev, "DMA not available, using PIO\n"); | ||
1623 | } | ||
1624 | #else | ||
1625 | static void atmci_configure_dma(struct atmel_mci *host) {} | ||
1595 | #endif | 1626 | #endif |
1596 | 1627 | ||
1597 | static int __init atmci_probe(struct platform_device *pdev) | 1628 | static int __init atmci_probe(struct platform_device *pdev) |
@@ -1645,22 +1676,7 @@ static int __init atmci_probe(struct platform_device *pdev) | |||
1645 | if (ret) | 1676 | if (ret) |
1646 | goto err_request_irq; | 1677 | goto err_request_irq; |
1647 | 1678 | ||
1648 | #ifdef CONFIG_MMC_ATMELMCI_DMA | 1679 | atmci_configure_dma(host); |
1649 | if (pdata->dma_slave.dma_dev) { | ||
1650 | struct dw_dma_slave *dws = &pdata->dma_slave; | ||
1651 | dma_cap_mask_t mask; | ||
1652 | |||
1653 | dws->tx_reg = regs->start + MCI_TDR; | ||
1654 | dws->rx_reg = regs->start + MCI_RDR; | ||
1655 | |||
1656 | /* Try to grab a DMA channel */ | ||
1657 | dma_cap_zero(mask); | ||
1658 | dma_cap_set(DMA_SLAVE, mask); | ||
1659 | host->dma.chan = dma_request_channel(mask, filter, dws); | ||
1660 | } | ||
1661 | if (!host->dma.chan) | ||
1662 | dev_notice(&pdev->dev, "DMA not available, using PIO\n"); | ||
1663 | #endif /* CONFIG_MMC_ATMELMCI_DMA */ | ||
1664 | 1680 | ||
1665 | platform_set_drvdata(pdev, host); | 1681 | platform_set_drvdata(pdev, host); |
1666 | 1682 | ||