Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

ASoC: atmel-pcm: use generic dmaengine framework

Align atmel pcm to use ASoC generic dmaengine framework

DMA is fully device tree based

Signed-off-by: Bo Shen <voice.shen@atmel.com>
Reviewed-by: Lars-Peter Clausen <lars@metafoo.de>
Signed-off-by: Mark Brown <broonie@linaro.org>

authored by

Bo Shen and committed by
Mark Brown
95e0e07e 10175b3b

+17 -88
+1
sound/soc/atmel/Kconfig
··· 13 13 config SND_ATMEL_SOC_DMA 14 14 tristate 15 15 depends on SND_ATMEL_SOC 16 + select SND_SOC_GENERIC_DMAENGINE_PCM 16 17 17 18 config SND_ATMEL_SOC_SSC 18 19 tristate
+16 -88
sound/soc/atmel/atmel-pcm-dma.c
··· 89 89 } 90 90 } 91 91 92 - /*--------------------------------------------------------------------------*\ 93 - * DMAENGINE operations 94 - \*--------------------------------------------------------------------------*/ 95 - static bool filter(struct dma_chan *chan, void *slave) 96 - { 97 - struct at_dma_slave *sl = slave; 98 - 99 - if (sl->dma_dev == chan->device->dev) { 100 - chan->private = sl; 101 - return true; 102 - } else { 103 - return false; 104 - } 105 - } 106 - 107 92 static int atmel_pcm_configure_dma(struct snd_pcm_substream *substream, 108 - struct snd_pcm_hw_params *params, struct atmel_pcm_dma_params *prtd) 93 + struct snd_pcm_hw_params *params, struct dma_slave_config *slave_config) 109 94 { 95 + struct snd_soc_pcm_runtime *rtd = substream->private_data; 96 + struct atmel_pcm_dma_params *prtd; 110 97 struct ssc_device *ssc; 111 - struct dma_chan *dma_chan; 112 - struct dma_slave_config slave_config; 113 98 int ret; 114 99 100 + prtd = snd_soc_dai_get_dma_data(rtd->cpu_dai, substream); 115 101 ssc = prtd->ssc; 116 102 117 - ret = snd_hwparams_to_dma_slave_config(substream, params, 118 - &slave_config); 103 + ret = snd_hwparams_to_dma_slave_config(substream, params, slave_config); 119 104 if (ret) { 120 105 pr_err("atmel-pcm: hwparams to dma slave configure failed\n"); 121 106 return ret; 122 107 } 123 108 124 109 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) { 125 - slave_config.dst_addr = (dma_addr_t)ssc->phybase + SSC_THR; 126 - slave_config.dst_maxburst = 1; 110 + slave_config->dst_addr = ssc->phybase + SSC_THR; 111 + slave_config->dst_maxburst = 1; 127 112 } else { 128 - slave_config.src_addr = (dma_addr_t)ssc->phybase + SSC_RHR; 129 - slave_config.src_maxburst = 1; 130 - } 131 - 132 - dma_chan = snd_dmaengine_pcm_get_chan(substream); 133 - if (dmaengine_slave_config(dma_chan, &slave_config)) { 134 - pr_err("atmel-pcm: failed to configure dma channel\n"); 135 - ret = -EBUSY; 136 - return ret; 137 - } 138 - 139 - return 0; 140 - } 141 - 142 - static int atmel_pcm_hw_params(struct snd_pcm_substream *substream, 143 - struct snd_pcm_hw_params *params) 144 - { 145 - struct snd_soc_pcm_runtime *rtd = substream->private_data; 146 - struct atmel_pcm_dma_params *prtd; 147 - struct ssc_device *ssc; 148 - struct at_dma_slave *sdata = NULL; 149 - int ret; 150 - 151 - snd_pcm_set_runtime_buffer(substream, &substream->dma_buffer); 152 - 153 - prtd = snd_soc_dai_get_dma_data(rtd->cpu_dai, substream); 154 - ssc = prtd->ssc; 155 - if (ssc->pdev) 156 - sdata = ssc->pdev->dev.platform_data; 157 - 158 - ret = snd_dmaengine_pcm_open_request_chan(substream, filter, sdata); 159 - if (ret) { 160 - pr_err("atmel-pcm: dmaengine pcm open failed\n"); 161 - return -EINVAL; 162 - } 163 - 164 - ret = atmel_pcm_configure_dma(substream, params, prtd); 165 - if (ret) { 166 - pr_err("atmel-pcm: failed to configure dmai\n"); 167 - goto err; 113 + slave_config->src_addr = ssc->phybase + SSC_RHR; 114 + slave_config->src_maxburst = 1; 168 115 } 169 116 170 117 prtd->dma_intr_handler = atmel_pcm_dma_irq; 171 118 172 119 return 0; 173 - err: 174 - snd_dmaengine_pcm_close_release_chan(substream); 175 - return ret; 176 120 } 177 121 178 - static int atmel_pcm_open(struct snd_pcm_substream *substream) 179 - { 180 - snd_soc_set_runtime_hwparams(substream, &atmel_pcm_dma_hardware); 181 - 182 - return 0; 183 - } 184 - 185 - static struct snd_pcm_ops atmel_pcm_ops = { 186 - .open = atmel_pcm_open, 187 - .close = snd_dmaengine_pcm_close_release_chan, 188 - .ioctl = snd_pcm_lib_ioctl, 189 - .hw_params = atmel_pcm_hw_params, 190 - .trigger = snd_dmaengine_pcm_trigger, 191 - .pointer = snd_dmaengine_pcm_pointer_no_residue, 192 - .mmap = atmel_pcm_mmap, 193 - }; 194 - 195 - static struct snd_soc_platform_driver atmel_soc_platform = { 196 - .ops = &atmel_pcm_ops, 197 - .pcm_new = atmel_pcm_new, 198 - .pcm_free = atmel_pcm_free, 122 + static const struct snd_dmaengine_pcm_config atmel_dmaengine_pcm_config = { 123 + .prepare_slave_config = atmel_pcm_configure_dma, 124 + .pcm_hardware = &atmel_pcm_dma_hardware, 125 + .prealloc_buffer_size = ATMEL_SSC_DMABUF_SIZE, 199 126 }; 200 127 201 128 int atmel_pcm_dma_platform_register(struct device *dev) 202 129 { 203 - return snd_soc_register_platform(dev, &atmel_soc_platform); 130 + return snd_dmaengine_pcm_register(dev, &atmel_dmaengine_pcm_config, 131 + SND_DMAENGINE_PCM_FLAG_NO_RESIDUE); 204 132 } 205 133 EXPORT_SYMBOL(atmel_pcm_dma_platform_register); 206 134 207 135 void atmel_pcm_dma_platform_unregister(struct device *dev) 208 136 { 209 - snd_soc_unregister_platform(dev); 137 + snd_dmaengine_pcm_unregister(dev); 210 138 } 211 139 EXPORT_SYMBOL(atmel_pcm_dma_platform_unregister); 212 140