aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/dma/dw
diff options
context:
space:
mode:
authorMans Rullgard <mans@mansr.com>2015-12-17 23:30:57 +0000
committerVinod Koul <vinod.koul@intel.com>2015-12-18 10:59:32 +0530
commit2b574ba9c50a06a1aa6cf908cd44119367111006 (patch)
tree5a4790db10d60ecc2befac8daea55252c4ba334d /drivers/dma/dw
parentdmaengine: img-mdc: Remove unnecessary synchronize_irq() before devm_free_irq() (diff)
downloadlinux-dev-2b574ba9c50a06a1aa6cf908cd44119367111006.tar.xz
linux-dev-2b574ba9c50a06a1aa6cf908cd44119367111006.zip
dmaengine: dw: fix potential memory leak in dw_dma_parse_dt()
If the "dma-channels" DT property is missing, the dw_dma_parse_dt() function return NULL, but not before allocating memory for a struct dw_dma_platform_data through devres. If the device supports parameter detection, the probe still succeeds and the allocated memory is not released until the device is removed. Fix this by deferring the allocation until after checking the "dma-channels" property. Signed-off-by: Mans Rullgard <mans@mansr.com> Acked-by: Viresh Kumar <viresh.kumar@linaro.org> Signed-off-by: Vinod Koul <vinod.koul@intel.com>
Diffstat (limited to 'drivers/dma/dw')
-rw-r--r--drivers/dma/dw/platform.c7
1 files changed, 5 insertions, 2 deletions
diff --git a/drivers/dma/dw/platform.c b/drivers/dma/dw/platform.c
index 68a4815750b5..5a417bbdfbd7 100644
--- a/drivers/dma/dw/platform.c
+++ b/drivers/dma/dw/platform.c
@@ -103,18 +103,21 @@ dw_dma_parse_dt(struct platform_device *pdev)
struct device_node *np = pdev->dev.of_node;
struct dw_dma_platform_data *pdata;
u32 tmp, arr[DW_DMA_MAX_NR_MASTERS];
+ u32 nr_channels;
if (!np) {
dev_err(&pdev->dev, "Missing DT data\n");
return NULL;
}
+ if (of_property_read_u32(np, "dma-channels", &nr_channels))
+ return NULL;
+
pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL);
if (!pdata)
return NULL;
- if (of_property_read_u32(np, "dma-channels", &pdata->nr_channels))
- return NULL;
+ pdata->nr_channels = nr_channels;
if (of_property_read_bool(np, "is_private"))
pdata->is_private = true;