[PATCH 3/3] ASoC: fsl_asrc_dma: allocate memory from dma device

Shengjiu Wang posted 3 patches 1 week, 5 days ago
There is a newer version of this series
[PATCH 3/3] ASoC: fsl_asrc_dma: allocate memory from dma device
Posted by Shengjiu Wang 1 week, 5 days ago
As the dma device may support dma-coherent property on the i.MX952,
allocate memory from dma device to make asrc driver to be compatible with
such a case.

Signed-off-by: Shengjiu Wang <shengjiu.wang@nxp.com>
---
 sound/soc/fsl/fsl_asrc_dma.c | 48 ++++++++++++++++++++++++++++++------
 1 file changed, 41 insertions(+), 7 deletions(-)

diff --git a/sound/soc/fsl/fsl_asrc_dma.c b/sound/soc/fsl/fsl_asrc_dma.c
index 7dacc06b2f02..b8fe242d53db 100644
--- a/sound/soc/fsl/fsl_asrc_dma.c
+++ b/sound/soc/fsl/fsl_asrc_dma.c
@@ -449,18 +449,52 @@ fsl_asrc_dma_pcm_pointer(struct snd_soc_component *component,
 static int fsl_asrc_dma_pcm_new(struct snd_soc_component *component,
 				struct snd_soc_pcm_runtime *rtd)
 {
-	struct snd_card *card = rtd->card->snd_card;
+	struct device *dev = component->dev;
+	struct fsl_asrc *asrc = dev_get_drvdata(dev);
+	struct fsl_asrc_pair *pair;
 	struct snd_pcm *pcm = rtd->pcm;
+	struct dma_chan *chan;
 	int ret;
 
-	ret = dma_coerce_mask_and_coherent(card->dev, DMA_BIT_MASK(32));
-	if (ret) {
-		dev_err(card->dev, "failed to set DMA mask\n");
-		return ret;
+	pair = kzalloc(sizeof(*pair) + asrc->pair_priv_size, GFP_KERNEL);
+	if (!pair)
+		return -ENOMEM;
+
+	pair->asrc = asrc;
+	pair->private = (void *)pair + sizeof(struct fsl_asrc_pair);
+
+	/* Request a dummy pair, which will be released later.
+	 * Request pair function needs channel num as input, for this
+	 * dummy pair, we just request "1" channel temporarily.
+	 */
+	ret = asrc->request_pair(1, pair);
+	if (ret < 0) {
+		dev_err(dev, "failed to request asrc pair\n");
+		goto req_pair_err;
 	}
 
-	return snd_pcm_set_fixed_buffer_all(pcm, SNDRV_DMA_TYPE_DEV,
-					    card->dev, FSL_ASRC_DMABUF_SIZE);
+	/* Request a dummy dma channel, which will be released later. */
+	chan = asrc->get_dma_channel(pair, IN);
+	if (!chan) {
+		dev_err(dev, "failed to get dma channel\n");
+		ret = -EINVAL;
+		goto dma_chan_err;
+	}
+
+	ret = snd_pcm_set_fixed_buffer_all(pcm,
+					   SNDRV_DMA_TYPE_DEV,
+					   chan->device->dev,
+					   FSL_ASRC_DMABUF_SIZE);
+
+	dma_release_channel(chan);
+
+dma_chan_err:
+	asrc->release_pair(pair);
+
+req_pair_err:
+	kfree(pair);
+
+	return ret;
 }
 
 struct snd_soc_component_driver fsl_asrc_component = {
-- 
2.34.1
Re: [PATCH 3/3] ASoC: fsl_asrc_dma: allocate memory from dma device
Posted by Frank Li 1 week, 3 days ago
On Wed, Jan 28, 2026 at 03:18:53PM +0800, Shengjiu Wang wrote:
> As the dma device may support dma-coherent property on the i.MX952,
> allocate memory from dma device to make asrc driver to be compatible with
> such a case.
>
> Signed-off-by: Shengjiu Wang <shengjiu.wang@nxp.com>
> ---
>  sound/soc/fsl/fsl_asrc_dma.c | 48 ++++++++++++++++++++++++++++++------
>  1 file changed, 41 insertions(+), 7 deletions(-)
>
> diff --git a/sound/soc/fsl/fsl_asrc_dma.c b/sound/soc/fsl/fsl_asrc_dma.c
> index 7dacc06b2f02..b8fe242d53db 100644
> --- a/sound/soc/fsl/fsl_asrc_dma.c
> +++ b/sound/soc/fsl/fsl_asrc_dma.c
> @@ -449,18 +449,52 @@ fsl_asrc_dma_pcm_pointer(struct snd_soc_component *component,
>  static int fsl_asrc_dma_pcm_new(struct snd_soc_component *component,
>  				struct snd_soc_pcm_runtime *rtd)
>  {
> -	struct snd_card *card = rtd->card->snd_card;
> +	struct device *dev = component->dev;
> +	struct fsl_asrc *asrc = dev_get_drvdata(dev);
> +	struct fsl_asrc_pair *pair;
>  	struct snd_pcm *pcm = rtd->pcm;
> +	struct dma_chan *chan;
>  	int ret;
>
> -	ret = dma_coerce_mask_and_coherent(card->dev, DMA_BIT_MASK(32));
> -	if (ret) {
> -		dev_err(card->dev, "failed to set DMA mask\n");
> -		return ret;
> +	pair = kzalloc(sizeof(*pair) + asrc->pair_priv_size, GFP_KERNEL);

prefer use size_add(sizeof(*pair), asrc->pair_priv_size), which did
overflow check.

> +	if (!pair)
> +		return -ENOMEM;
> +
> +	pair->asrc = asrc;
> +	pair->private = (void *)pair + sizeof(struct fsl_asrc_pair);
> +
> +	/* Request a dummy pair, which will be released later.
> +	 * Request pair function needs channel num as input, for this
> +	 * dummy pair, we just request "1" channel temporarily.
> +	 */
> +	ret = asrc->request_pair(1, pair);
> +	if (ret < 0) {
> +		dev_err(dev, "failed to request asrc pair\n");
> +		goto req_pair_err;
>  	}
>
> -	return snd_pcm_set_fixed_buffer_all(pcm, SNDRV_DMA_TYPE_DEV,
> -					    card->dev, FSL_ASRC_DMABUF_SIZE);
> +	/* Request a dummy dma channel, which will be released later. */
> +	chan = asrc->get_dma_channel(pair, IN);

Is it possible get real dma chan from fsl_asrc?

> +	if (!chan) {
> +		dev_err(dev, "failed to get dma channel\n");
> +		ret = -EINVAL;
> +		goto dma_chan_err;
> +	}
> +
> +	ret = snd_pcm_set_fixed_buffer_all(pcm,
> +					   SNDRV_DMA_TYPE_DEV,
> +					   chan->device->dev,
> +					   FSL_ASRC_DMABUF_SIZE);

Here you assume chan->device->dev never change when it did DMA transfer.

Frank
> +
> +	dma_release_channel(chan);
> +
> +dma_chan_err:
> +	asrc->release_pair(pair);
> +
> +req_pair_err:
> +	kfree(pair);
> +
> +	return ret;
>  }
>
>  struct snd_soc_component_driver fsl_asrc_component = {
> --
> 2.34.1
>
Re: [PATCH 3/3] ASoC: fsl_asrc_dma: allocate memory from dma device
Posted by Shengjiu Wang 1 week, 3 days ago
On Fri, Jan 30, 2026 at 1:09 AM Frank Li <Frank.li@nxp.com> wrote:
>
> On Wed, Jan 28, 2026 at 03:18:53PM +0800, Shengjiu Wang wrote:
> > As the dma device may support dma-coherent property on the i.MX952,
> > allocate memory from dma device to make asrc driver to be compatible with
> > such a case.
> >
> > Signed-off-by: Shengjiu Wang <shengjiu.wang@nxp.com>
> > ---
> >  sound/soc/fsl/fsl_asrc_dma.c | 48 ++++++++++++++++++++++++++++++------
> >  1 file changed, 41 insertions(+), 7 deletions(-)
> >
> > diff --git a/sound/soc/fsl/fsl_asrc_dma.c b/sound/soc/fsl/fsl_asrc_dma.c
> > index 7dacc06b2f02..b8fe242d53db 100644
> > --- a/sound/soc/fsl/fsl_asrc_dma.c
> > +++ b/sound/soc/fsl/fsl_asrc_dma.c
> > @@ -449,18 +449,52 @@ fsl_asrc_dma_pcm_pointer(struct snd_soc_component *component,
> >  static int fsl_asrc_dma_pcm_new(struct snd_soc_component *component,
> >                               struct snd_soc_pcm_runtime *rtd)
> >  {
> > -     struct snd_card *card = rtd->card->snd_card;
> > +     struct device *dev = component->dev;
> > +     struct fsl_asrc *asrc = dev_get_drvdata(dev);
> > +     struct fsl_asrc_pair *pair;
> >       struct snd_pcm *pcm = rtd->pcm;
> > +     struct dma_chan *chan;
> >       int ret;
> >
> > -     ret = dma_coerce_mask_and_coherent(card->dev, DMA_BIT_MASK(32));
> > -     if (ret) {
> > -             dev_err(card->dev, "failed to set DMA mask\n");
> > -             return ret;
> > +     pair = kzalloc(sizeof(*pair) + asrc->pair_priv_size, GFP_KERNEL);
>
> prefer use size_add(sizeof(*pair), asrc->pair_priv_size), which did
> overflow check.

Ok, will update it.

>
> > +     if (!pair)
> > +             return -ENOMEM;
> > +
> > +     pair->asrc = asrc;
> > +     pair->private = (void *)pair + sizeof(struct fsl_asrc_pair);
> > +
> > +     /* Request a dummy pair, which will be released later.
> > +      * Request pair function needs channel num as input, for this
> > +      * dummy pair, we just request "1" channel temporarily.
> > +      */
> > +     ret = asrc->request_pair(1, pair);
> > +     if (ret < 0) {
> > +             dev_err(dev, "failed to request asrc pair\n");
> > +             goto req_pair_err;
> >       }
> >
> > -     return snd_pcm_set_fixed_buffer_all(pcm, SNDRV_DMA_TYPE_DEV,
> > -                                         card->dev, FSL_ASRC_DMABUF_SIZE);
> > +     /* Request a dummy dma channel, which will be released later. */
> > +     chan = asrc->get_dma_channel(pair, IN);
>
> Is it possible get real dma chan from fsl_asrc?

This is real dma chan, may be I should remove "dummy".

>
> > +     if (!chan) {
> > +             dev_err(dev, "failed to get dma channel\n");
> > +             ret = -EINVAL;
> > +             goto dma_chan_err;
> > +     }
> > +
> > +     ret = snd_pcm_set_fixed_buffer_all(pcm,
> > +                                        SNDRV_DMA_TYPE_DEV,
> > +                                        chan->device->dev,
> > +                                        FSL_ASRC_DMABUF_SIZE);
>
> Here you assume chan->device->dev never change when it did DMA transfer.

Yes, this refers to the generic code in ALSA.

best regards
Shengjiu Wang

>
> Frank
> > +
> > +     dma_release_channel(chan);
> > +
> > +dma_chan_err:
> > +     asrc->release_pair(pair);
> > +
> > +req_pair_err:
> > +     kfree(pair);
> > +
> > +     return ret;
> >  }
> >
> >  struct snd_soc_component_driver fsl_asrc_component = {
> > --
> > 2.34.1
> >
Re: [PATCH 3/3] ASoC: fsl_asrc_dma: allocate memory from dma device
Posted by Daniel Baluta 1 week, 4 days ago
On 1/28/26 09:18, Shengjiu Wang wrote:
> As the dma device may support dma-coherent property on the i.MX952,
> allocate memory from dma device to make asrc driver to be compatible with
> such a case.


This commit message refers to imx952 but the change in the code apply to all supported platforms

So in not really clear what is the intention of it.

Also, it is not clear why do you allocate a pair only to free it at the end of the function.
Re: [PATCH 3/3] ASoC: fsl_asrc_dma: allocate memory from dma device
Posted by Shengjiu Wang 1 week, 4 days ago
On Thu, Jan 29, 2026 at 5:22 PM Daniel Baluta <daniel.baluta@oss.nxp.com> wrote:
>
> On 1/28/26 09:18, Shengjiu Wang wrote:
> > As the dma device may support dma-coherent property on the i.MX952,
> > allocate memory from dma device to make asrc driver to be compatible with
> > such a case.
>
>
> This commit message refers to imx952 but the change in the code apply to all supported platforms
>
> So in not really clear what is the intention of it.

The dma-coherent property is used to indicate a device is capable of
coherent DMA operations.
Which is applied to the EDMA device on i.MX952,  in order to support
such EDMA device,
the memory is need to allocated from DMA device,

The code change is compatible for non dma-coherent and dma-coherent dma devices.

>
> Also, it is not clear why do you allocate a pair only to free it at the end of the function.

As the comment in the code says,  it is to get the dma device handler
for memory allocation
. After that, it is freed.

best regards
Shengjiu wang
>
>