aboutsummaryrefslogtreecommitdiffstats
path: root/sound/soc/intel/sst-mfld-platform-pcm.c
diff options
context:
space:
mode:
authorVinod Koul <vinod.koul@intel.com>2014-06-13 08:33:56 -0400
committerMark Brown <broonie@linaro.org>2014-06-23 07:24:27 -0400
commit61b165caa686b8334379293d0e241f740fac195a (patch)
treebd192f4a4a3cdf617ef1d580140066dfec68f210 /sound/soc/intel/sst-mfld-platform-pcm.c
parenta870cdce9edc57d0196e7ae9cad8acc5720cd709 (diff)
ASoC: Intel: add mrfld pipelines
Merrifield DSP used various pipelines to identify the streams and processing modules. Add these defination in the pcm driver and also add a table for device entries to firmware pipeline id conversion Signed-off-by: Vinod Koul <vinod.koul@intel.com> Signed-off-by: Mark Brown <broonie@linaro.org>
Diffstat (limited to 'sound/soc/intel/sst-mfld-platform-pcm.c')
-rw-r--r--sound/soc/intel/sst-mfld-platform-pcm.c100
1 files changed, 91 insertions, 9 deletions
diff --git a/sound/soc/intel/sst-mfld-platform-pcm.c b/sound/soc/intel/sst-mfld-platform-pcm.c
index 6e7bfb1bc4aa..7de87887d9f8 100644
--- a/sound/soc/intel/sst-mfld-platform-pcm.c
+++ b/sound/soc/intel/sst-mfld-platform-pcm.c
@@ -1,7 +1,7 @@
1/* 1/*
2 * sst_mfld_platform.c - Intel MID Platform driver 2 * sst_mfld_platform.c - Intel MID Platform driver
3 * 3 *
4 * Copyright (C) 2010-2013 Intel Corp 4 * Copyright (C) 2010-2014 Intel Corp
5 * Author: Vinod Koul <vinod.koul@intel.com> 5 * Author: Vinod Koul <vinod.koul@intel.com>
6 * Author: Harsha Priya <priya.harsha@intel.com> 6 * Author: Harsha Priya <priya.harsha@intel.com>
7 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 7 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
@@ -27,7 +27,9 @@
27#include <sound/pcm_params.h> 27#include <sound/pcm_params.h>
28#include <sound/soc.h> 28#include <sound/soc.h>
29#include <sound/compress_driver.h> 29#include <sound/compress_driver.h>
30#include <asm/platform_sst_audio.h>
30#include "sst-mfld-platform.h" 31#include "sst-mfld-platform.h"
32#include "sst-atom-controls.h"
31 33
32struct sst_device *sst; 34struct sst_device *sst;
33static DEFINE_MUTEX(sst_lock); 35static DEFINE_MUTEX(sst_lock);
@@ -92,6 +94,13 @@ static struct snd_pcm_hardware sst_platform_pcm_hw = {
92 .fifo_size = SST_FIFO_SIZE, 94 .fifo_size = SST_FIFO_SIZE,
93}; 95};
94 96
97static struct sst_dev_stream_map dpcm_strm_map[] = {
98 {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}, /* Reserved, not in use */
99 {MERR_DPCM_AUDIO, 0, SNDRV_PCM_STREAM_PLAYBACK, PIPE_MEDIA1_IN, SST_TASK_ID_MEDIA, 0},
100 {MERR_DPCM_COMPR, 0, SNDRV_PCM_STREAM_PLAYBACK, PIPE_MEDIA0_IN, SST_TASK_ID_MEDIA, 0},
101 {MERR_DPCM_AUDIO, 0, SNDRV_PCM_STREAM_CAPTURE, PIPE_PCM1_OUT, SST_TASK_ID_MEDIA, 0},
102};
103
95/* MFLD - MSIC */ 104/* MFLD - MSIC */
96static struct snd_soc_dai_driver sst_platform_dai[] = { 105static struct snd_soc_dai_driver sst_platform_dai[] = {
97{ 106{
@@ -175,12 +184,36 @@ static void sst_fill_pcm_params(struct snd_pcm_substream *substream,
175 memset(param->uc.pcm_params.channel_map, 0, sizeof(u8)); 184 memset(param->uc.pcm_params.channel_map, 0, sizeof(u8));
176 185
177} 186}
187
188static int sst_get_stream_mapping(int dev, int sdev, int dir,
189 struct sst_dev_stream_map *map, int size)
190{
191 int i;
192
193 if (map == NULL)
194 return -EINVAL;
195
196
197 /* index 0 is not used in stream map */
198 for (i = 1; i < size; i++) {
199 if ((map[i].dev_num == dev) && (map[i].direction == dir))
200 return i;
201 }
202 return 0;
203}
204
178int sst_fill_stream_params(void *substream, 205int sst_fill_stream_params(void *substream,
179 struct snd_sst_params *str_params, bool is_compress) 206 const struct sst_data *ctx, struct snd_sst_params *str_params, bool is_compress)
180{ 207{
208 int map_size;
209 int index;
210 struct sst_dev_stream_map *map;
181 struct snd_pcm_substream *pstream = NULL; 211 struct snd_pcm_substream *pstream = NULL;
182 struct snd_compr_stream *cstream = NULL; 212 struct snd_compr_stream *cstream = NULL;
183 213
214 map = ctx->pdata->pdev_strm_map;
215 map_size = ctx->pdata->strm_map_size;
216
184 if (is_compress == true) 217 if (is_compress == true)
185 cstream = (struct snd_compr_stream *)substream; 218 cstream = (struct snd_compr_stream *)substream;
186 else 219 else
@@ -189,11 +222,32 @@ int sst_fill_stream_params(void *substream,
189 str_params->stream_type = SST_STREAM_TYPE_MUSIC; 222 str_params->stream_type = SST_STREAM_TYPE_MUSIC;
190 223
191 /* For pcm streams */ 224 /* For pcm streams */
192 if (pstream) 225 if (pstream) {
226 index = sst_get_stream_mapping(pstream->pcm->device,
227 pstream->number, pstream->stream,
228 map, map_size);
229 if (index <= 0)
230 return -EINVAL;
231
232 str_params->stream_id = index;
233 str_params->device_type = map[index].device_id;
234 str_params->task = map[index].task_id;
235
193 str_params->ops = (u8)pstream->stream; 236 str_params->ops = (u8)pstream->stream;
194 if (cstream) 237 }
195 str_params->ops = (u8)cstream->direction; 238
239 if (cstream) {
240 index = sst_get_stream_mapping(cstream->device->device,
241 0, cstream->direction,
242 map, map_size);
243 if (index <= 0)
244 return -EINVAL;
245 str_params->stream_id = index;
246 str_params->device_type = map[index].device_id;
247 str_params->task = map[index].task_id;
196 248
249 str_params->ops = (u8)cstream->direction;
250 }
197 return 0; 251 return 0;
198} 252}
199 253
@@ -206,6 +260,7 @@ static int sst_platform_alloc_stream(struct snd_pcm_substream *substream,
206 struct snd_sst_params str_params = {0}; 260 struct snd_sst_params str_params = {0};
207 struct snd_sst_alloc_params_ext alloc_params = {0}; 261 struct snd_sst_alloc_params_ext alloc_params = {0};
208 int ret_val = 0; 262 int ret_val = 0;
263 struct sst_data *ctx = snd_soc_platform_get_drvdata(platform);
209 264
210 /* set codec params and inform SST driver the same */ 265 /* set codec params and inform SST driver the same */
211 sst_fill_pcm_params(substream, &param); 266 sst_fill_pcm_params(substream, &param);
@@ -216,7 +271,7 @@ static int sst_platform_alloc_stream(struct snd_pcm_substream *substream,
216 str_params.codec = SST_CODEC_TYPE_PCM; 271 str_params.codec = SST_CODEC_TYPE_PCM;
217 272
218 /* fill the device type and stream id to pass to SST driver */ 273 /* fill the device type and stream id to pass to SST driver */
219 ret_val = sst_fill_stream_params(substream, &str_params, false); 274 ret_val = sst_fill_stream_params(substream, ctx, &str_params, false);
220 if (ret_val < 0) 275 if (ret_val < 0)
221 return ret_val; 276 return ret_val;
222 277
@@ -321,7 +376,22 @@ static void sst_media_close(struct snd_pcm_substream *substream,
321 ret_val = stream->ops->close(str_id); 376 ret_val = stream->ops->close(str_id);
322 module_put(sst->dev->driver->owner); 377 module_put(sst->dev->driver->owner);
323 kfree(stream); 378 kfree(stream);
324 return; 379}
380
381static inline unsigned int get_current_pipe_id(struct snd_soc_platform *platform,
382 struct snd_pcm_substream *substream)
383{
384 struct sst_data *sst = snd_soc_platform_get_drvdata(platform);
385 struct sst_dev_stream_map *map = sst->pdata->pdev_strm_map;
386 struct sst_runtime_stream *stream =
387 substream->runtime->private_data;
388 u32 str_id = stream->stream_info.str_id;
389 unsigned int pipe_id;
390 pipe_id = map[str_id].device_id;
391
392 pr_debug("%s: got pipe_id = %#x for str_id = %d\n",
393 __func__, pipe_id, str_id);
394 return pipe_id;
325} 395}
326 396
327static int sst_media_prepare(struct snd_pcm_substream *substream, 397static int sst_media_prepare(struct snd_pcm_substream *substream,
@@ -498,10 +568,22 @@ static const struct snd_soc_component_driver sst_component = {
498 568
499static int sst_platform_probe(struct platform_device *pdev) 569static int sst_platform_probe(struct platform_device *pdev)
500{ 570{
571 struct sst_data *drv;
501 int ret; 572 int ret;
573 struct sst_platform_data *pdata = pdev->dev.platform_data;
574
575 drv = devm_kzalloc(&pdev->dev, sizeof(*drv), GFP_KERNEL);
576 if (sst == NULL) {
577 pr_err("kzalloc failed\n");
578 return -ENOMEM;
579 }
580
581 pdata->pdev_strm_map = dpcm_strm_map;
582 pdata->strm_map_size = ARRAY_SIZE(dpcm_strm_map);
583 drv->pdata = pdata;
584 mutex_init(&drv->lock);
585 dev_set_drvdata(&pdev->dev, drv);
502 586
503 pr_debug("sst_platform_probe called\n");
504 sst = NULL;
505 ret = snd_soc_register_platform(&pdev->dev, &sst_soc_platform_drv); 587 ret = snd_soc_register_platform(&pdev->dev, &sst_soc_platform_drv);
506 if (ret) { 588 if (ret) {
507 pr_err("registering soc platform failed\n"); 589 pr_err("registering soc platform failed\n");