| From 5d0330316bfbce0b6819e8842f6c965ad1053d9c Mon Sep 17 00:00:00 2001 |
| From: Guennadi Liakhovetski <g.liakhovetski@gmx.de> |
| Date: Tue, 2 Jul 2013 17:45:55 +0200 |
| Subject: DMA: shdma: switch to managed resource allocation |
| |
| Switch shdma to using devm_* managed functions for allocation of memory, |
| requesting IRQs, mapping IO resources etc. |
| |
| Signed-off-by: Guennadi Liakhovetski <g.liakhovetski+renesas@gmail.com> |
| Signed-off-by: Vinod Koul <vinod.koul@intel.com> |
| (cherry picked from commit c1c63a14f4f2419d093acd7164eccdff315baa86) |
| Signed-off-by: Simon Horman <horms+renesas@verge.net.au> |
| --- |
| drivers/dma/sh/shdma-base.c | 11 ++------ |
| drivers/dma/sh/shdma.c | 66 +++++++++------------------------------------ |
| drivers/dma/sh/sudmac.c | 1 - |
| include/linux/shdma-base.h | 1 - |
| 4 files changed, 15 insertions(+), 64 deletions(-) |
| |
| diff --git a/drivers/dma/sh/shdma-base.c b/drivers/dma/sh/shdma-base.c |
| index 28ca36121631..c5ea256c2819 100644 |
| --- a/drivers/dma/sh/shdma-base.c |
| +++ b/drivers/dma/sh/shdma-base.c |
| @@ -831,8 +831,8 @@ static irqreturn_t chan_irqt(int irq, void *dev) |
| int shdma_request_irq(struct shdma_chan *schan, int irq, |
| unsigned long flags, const char *name) |
| { |
| - int ret = request_threaded_irq(irq, chan_irq, chan_irqt, |
| - flags, name, schan); |
| + int ret = devm_request_threaded_irq(schan->dev, irq, chan_irq, |
| + chan_irqt, flags, name, schan); |
| |
| schan->irq = ret < 0 ? ret : irq; |
| |
| @@ -840,13 +840,6 @@ int shdma_request_irq(struct shdma_chan *schan, int irq, |
| } |
| EXPORT_SYMBOL(shdma_request_irq); |
| |
| -void shdma_free_irq(struct shdma_chan *schan) |
| -{ |
| - if (schan->irq >= 0) |
| - free_irq(schan->irq, schan); |
| -} |
| -EXPORT_SYMBOL(shdma_free_irq); |
| - |
| void shdma_chan_probe(struct shdma_dev *sdev, |
| struct shdma_chan *schan, int id) |
| { |
| diff --git a/drivers/dma/sh/shdma.c b/drivers/dma/sh/shdma.c |
| index ba539d8cabee..4f24b9d2b5c3 100644 |
| --- a/drivers/dma/sh/shdma.c |
| +++ b/drivers/dma/sh/shdma.c |
| @@ -515,7 +515,8 @@ static int sh_dmae_chan_probe(struct sh_dmae_device *shdev, int id, |
| struct shdma_chan *schan; |
| int err; |
| |
| - sh_chan = kzalloc(sizeof(struct sh_dmae_chan), GFP_KERNEL); |
| + sh_chan = devm_kzalloc(sdev->dma_dev.dev, sizeof(struct sh_dmae_chan), |
| + GFP_KERNEL); |
| if (!sh_chan) { |
| dev_err(sdev->dma_dev.dev, |
| "No free memory for allocating dma channels!\n"); |
| @@ -551,7 +552,6 @@ static int sh_dmae_chan_probe(struct sh_dmae_device *shdev, int id, |
| err_no_irq: |
| /* remove from dmaengine device node */ |
| shdma_chan_remove(schan); |
| - kfree(sh_chan); |
| return err; |
| } |
| |
| @@ -562,14 +562,9 @@ static void sh_dmae_chan_remove(struct sh_dmae_device *shdev) |
| int i; |
| |
| shdma_for_each_chan(schan, &shdev->shdma_dev, i) { |
| - struct sh_dmae_chan *sh_chan = container_of(schan, |
| - struct sh_dmae_chan, shdma_chan); |
| BUG_ON(!schan); |
| |
| - shdma_free_irq(&sh_chan->shdma_chan); |
| - |
| shdma_chan_remove(schan); |
| - kfree(sh_chan); |
| } |
| dma_dev->chancnt = 0; |
| } |
| @@ -706,33 +701,22 @@ static int sh_dmae_probe(struct platform_device *pdev) |
| if (!chan || !errirq_res) |
| return -ENODEV; |
| |
| - if (!request_mem_region(chan->start, resource_size(chan), pdev->name)) { |
| - dev_err(&pdev->dev, "DMAC register region already claimed\n"); |
| - return -EBUSY; |
| - } |
| - |
| - if (dmars && !request_mem_region(dmars->start, resource_size(dmars), pdev->name)) { |
| - dev_err(&pdev->dev, "DMAC DMARS region already claimed\n"); |
| - err = -EBUSY; |
| - goto ermrdmars; |
| - } |
| - |
| - err = -ENOMEM; |
| - shdev = kzalloc(sizeof(struct sh_dmae_device), GFP_KERNEL); |
| + shdev = devm_kzalloc(&pdev->dev, sizeof(struct sh_dmae_device), |
| + GFP_KERNEL); |
| if (!shdev) { |
| dev_err(&pdev->dev, "Not enough memory\n"); |
| - goto ealloc; |
| + return -ENOMEM; |
| } |
| |
| dma_dev = &shdev->shdma_dev.dma_dev; |
| |
| - shdev->chan_reg = ioremap(chan->start, resource_size(chan)); |
| - if (!shdev->chan_reg) |
| - goto emapchan; |
| + shdev->chan_reg = devm_ioremap_resource(&pdev->dev, chan); |
| + if (IS_ERR(shdev->chan_reg)) |
| + return PTR_ERR(shdev->chan_reg); |
| if (dmars) { |
| - shdev->dmars = ioremap(dmars->start, resource_size(dmars)); |
| - if (!shdev->dmars) |
| - goto emapdmars; |
| + shdev->dmars = devm_ioremap_resource(&pdev->dev, dmars); |
| + if (IS_ERR(shdev->dmars)) |
| + return PTR_ERR(shdev->dmars); |
| } |
| |
| if (!pdata->slave_only) |
| @@ -793,8 +777,8 @@ static int sh_dmae_probe(struct platform_device *pdev) |
| |
| errirq = errirq_res->start; |
| |
| - err = request_irq(errirq, sh_dmae_err, irqflags, |
| - "DMAC Address Error", shdev); |
| + err = devm_request_irq(&pdev->dev, errirq, sh_dmae_err, irqflags, |
| + "DMAC Address Error", shdev); |
| if (err) { |
| dev_err(&pdev->dev, |
| "DMA failed requesting irq #%d, error %d\n", |
| @@ -872,7 +856,6 @@ chan_probe_err: |
| sh_dmae_chan_remove(shdev); |
| |
| #if defined(CONFIG_CPU_SH4) || defined(CONFIG_ARCH_SHMOBILE) |
| - free_irq(errirq, shdev); |
| eirq_err: |
| #endif |
| rst_err: |
| @@ -886,18 +869,7 @@ rst_err: |
| platform_set_drvdata(pdev, NULL); |
| shdma_cleanup(&shdev->shdma_dev); |
| eshdma: |
| - if (dmars) |
| - iounmap(shdev->dmars); |
| -emapdmars: |
| - iounmap(shdev->chan_reg); |
| synchronize_rcu(); |
| -emapchan: |
| - kfree(shdev); |
| -ealloc: |
| - if (dmars) |
| - release_mem_region(dmars->start, resource_size(dmars)); |
| -ermrdmars: |
| - release_mem_region(chan->start, resource_size(chan)); |
| |
| return err; |
| } |
| @@ -923,21 +895,9 @@ static int sh_dmae_remove(struct platform_device *pdev) |
| sh_dmae_chan_remove(shdev); |
| shdma_cleanup(&shdev->shdma_dev); |
| |
| - if (shdev->dmars) |
| - iounmap(shdev->dmars); |
| - iounmap(shdev->chan_reg); |
| - |
| platform_set_drvdata(pdev, NULL); |
| |
| synchronize_rcu(); |
| - kfree(shdev); |
| - |
| - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| - if (res) |
| - release_mem_region(res->start, resource_size(res)); |
| - res = platform_get_resource(pdev, IORESOURCE_MEM, 1); |
| - if (res) |
| - release_mem_region(res->start, resource_size(res)); |
| |
| return 0; |
| } |
| diff --git a/drivers/dma/sh/sudmac.c b/drivers/dma/sh/sudmac.c |
| index e7c94bbddb53..347790167e59 100644 |
| --- a/drivers/dma/sh/sudmac.c |
| +++ b/drivers/dma/sh/sudmac.c |
| @@ -302,7 +302,6 @@ static void sudmac_chan_remove(struct sudmac_device *su_dev) |
| |
| BUG_ON(!schan); |
| |
| - shdma_free_irq(&sc->shdma_chan); |
| shdma_chan_remove(schan); |
| } |
| dma_dev->chancnt = 0; |
| diff --git a/include/linux/shdma-base.h b/include/linux/shdma-base.h |
| index 5b1c9848124c..31cf89fb1d5b 100644 |
| --- a/include/linux/shdma-base.h |
| +++ b/include/linux/shdma-base.h |
| @@ -116,7 +116,6 @@ struct shdma_dev { |
| |
| int shdma_request_irq(struct shdma_chan *, int, |
| unsigned long, const char *); |
| -void shdma_free_irq(struct shdma_chan *); |
| bool shdma_reset(struct shdma_dev *sdev); |
| void shdma_chan_probe(struct shdma_dev *sdev, |
| struct shdma_chan *schan, int id); |
| -- |
| 1.8.5.rc3 |
| |