Use a flexible array member to combine kzalloc and kcalloc to a single allocation.
Add __counted_by for extra runtime analysis. Assign counting variable after allocation as required by __counted_by. Signed-off-by: Rosen Penev <[email protected]> --- drivers/dma/st_fdma.c | 27 ++++++++------------------- drivers/dma/st_fdma.h | 4 ++-- 2 files changed, 10 insertions(+), 21 deletions(-) diff --git a/drivers/dma/st_fdma.c b/drivers/dma/st_fdma.c index d9547017f3bd..3ec0d6731b8d 100644 --- a/drivers/dma/st_fdma.c +++ b/drivers/dma/st_fdma.c @@ -710,16 +710,6 @@ static const struct of_device_id st_fdma_match[] = { }; MODULE_DEVICE_TABLE(of, st_fdma_match); -static int st_fdma_parse_dt(struct platform_device *pdev, - const struct st_fdma_driverdata *drvdata, - struct st_fdma_dev *fdev) -{ - snprintf(fdev->fw_name, FW_NAME_SIZE, "fdma_%s_%d.elf", - drvdata->name, drvdata->id); - - return of_property_read_u32(pdev->dev.of_node, "dma-channels", - &fdev->nr_channels); -} #define FDMA_DMA_BUSWIDTHS (BIT(DMA_SLAVE_BUSWIDTH_1_BYTE) | \ BIT(DMA_SLAVE_BUSWIDTH_2_BYTES) | \ BIT(DMA_SLAVE_BUSWIDTH_3_BYTES) | \ @@ -742,27 +732,26 @@ static int st_fdma_probe(struct platform_device *pdev) struct st_fdma_dev *fdev; struct device_node *np = pdev->dev.of_node; const struct st_fdma_driverdata *drvdata; + u32 nr_channels; int ret, i; drvdata = device_get_match_data(&pdev->dev); - fdev = devm_kzalloc(&pdev->dev, sizeof(*fdev), GFP_KERNEL); - if (!fdev) - return -ENOMEM; - - ret = st_fdma_parse_dt(pdev, drvdata, fdev); + ret = of_property_read_u32(pdev->dev.of_node, "dma-channels", &nr_channels); if (ret) { dev_err(&pdev->dev, "unable to find platform data\n"); - goto err; + return ret; } - fdev->chans = devm_kcalloc(&pdev->dev, fdev->nr_channels, - sizeof(struct st_fdma_chan), GFP_KERNEL); - if (!fdev->chans) + fdev = devm_kzalloc(&pdev->dev, struct_size(fdev, chans, nr_channels), GFP_KERNEL); + if (!fdev) return -ENOMEM; + fdev->nr_channels = nr_channels; fdev->dev = &pdev->dev; fdev->drvdata = drvdata; + snprintf(fdev->fw_name, FW_NAME_SIZE, "fdma_%s_%d.elf", drvdata->name, drvdata->id); + platform_set_drvdata(pdev, fdev); fdev->irq = platform_get_irq(pdev, 0); diff --git a/drivers/dma/st_fdma.h b/drivers/dma/st_fdma.h index f1e746f7bc7d..27ded555879f 100644 --- a/drivers/dma/st_fdma.h +++ b/drivers/dma/st_fdma.h @@ -136,13 +136,13 @@ struct st_fdma_dev { int irq; - struct st_fdma_chan *chans; - spinlock_t dreq_lock; unsigned long dreq_mask; u32 nr_channels; char fw_name[FW_NAME_SIZE]; + + struct st_fdma_chan chans[] __counted_by(nr_channels); }; /* Peripheral Registers*/ -- 2.53.0

