aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLiam Girdwood <lrg@ti.com>2011-07-24 15:59:43 -0400
committerPaolo Pisati <paolo.pisati@canonical.com>2012-08-17 04:18:25 -0400
commitd4363e11fe690f28ef3043c3e913839a34d22030 (patch)
treeb70e0d7e8f2c33639d04ff07d9e7133fb44f47ba
parent47ab6540593de31edf24ec22220b26e642651f02 (diff)
Subject: [PATCH 071/104] ASoC: dsp - Add DSP support to core ASoC API/structures
Export inline DAI PCM operations to allow DSP core to individually call BE PCM operations and .... Allow machine drivers to specifify DSP FE and BE DAI links. Add FE and BE state information to PCM rtd. TODO: split out this into smaller patches. Signed-off-by: Liam Girdwood <lrg@ti.com>
-rw-r--r--include/sound/soc-dai.h94
-rw-r--r--include/sound/soc.h38
-rw-r--r--sound/soc/soc-core.c2
3 files changed, 133 insertions, 1 deletions
diff --git a/include/sound/soc-dai.h b/include/sound/soc-dai.h
index 5ad5f3a50c6..f298f67b954 100644
--- a/include/sound/soc-dai.h
+++ b/include/sound/soc-dai.h
@@ -281,4 +281,98 @@ static inline void *snd_soc_dai_get_drvdata(struct snd_soc_dai *dai)
281 return dev_get_drvdata(dai->dev); 281 return dev_get_drvdata(dai->dev);
282} 282}
283 283
284/* Backend DAI PCM ops */
285static inline int snd_soc_dai_startup(struct snd_pcm_substream *substream,
286 struct snd_soc_dai *dai)
287{
288 struct snd_soc_pcm_runtime *rtd = substream->private_data;
289 int ret = 0;
290
291 mutex_lock(&rtd->pcm_mutex);
292
293 if (dai->driver->ops->startup)
294 ret = dai->driver->ops->startup(substream, dai);
295
296 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
297 dai->playback_active++;
298 else
299 dai->capture_active++;
300
301 dai->active++;
302
303 mutex_unlock(&rtd->pcm_mutex);
304 return ret;
305}
306
307static inline void snd_soc_dai_shutdown(struct snd_pcm_substream *substream,
308 struct snd_soc_dai *dai)
309{
310 struct snd_soc_pcm_runtime *rtd = substream->private_data;
311
312 mutex_lock(&rtd->pcm_mutex);
313
314 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
315 dai->playback_active--;
316 else
317 dai->capture_active--;
318
319 dai->active--;
320
321 if (dai->driver->ops->shutdown)
322 dai->driver->ops->shutdown(substream, dai);
323 mutex_unlock(&rtd->pcm_mutex);
324}
325
326static inline int snd_soc_dai_hw_params(struct snd_pcm_substream * substream,
327 struct snd_pcm_hw_params *hw_params, struct snd_soc_dai *dai)
328{
329 struct snd_soc_pcm_runtime *rtd = substream->private_data;
330 int ret = 0;
331
332 mutex_lock(&rtd->pcm_mutex);
333
334 if (dai->driver->ops->hw_params)
335 ret = dai->driver->ops->hw_params(substream, hw_params, dai);
336
337 mutex_unlock(&rtd->pcm_mutex);
338 return ret;
339}
340
341static inline int snd_soc_dai_hw_free(struct snd_pcm_substream *substream,
342 struct snd_soc_dai *dai)
343{
344 struct snd_soc_pcm_runtime *rtd = substream->private_data;
345 int ret = 0;
346
347 mutex_lock(&rtd->pcm_mutex);
348
349 if (dai->driver->ops->hw_free)
350 ret = dai->driver->ops->hw_free(substream, dai);
351
352 mutex_unlock(&rtd->pcm_mutex);
353 return ret;
354}
355
356static inline int snd_soc_dai_prepare(struct snd_pcm_substream *substream,
357 struct snd_soc_dai *dai)
358{
359 struct snd_soc_pcm_runtime *rtd = substream->private_data;
360 int ret = 0;
361
362 mutex_lock(&rtd->pcm_mutex);
363
364 if (dai->driver->ops->prepare)
365 ret = dai->driver->ops->prepare(substream, dai);
366
367 mutex_unlock(&rtd->pcm_mutex);
368 return ret;
369}
370
371static inline int snd_soc_dai_trigger(struct snd_pcm_substream *substream,
372 int cmd, struct snd_soc_dai *dai)
373{
374 if (dai->driver->ops->trigger)
375 return dai->driver->ops->trigger(substream, cmd, dai);
376 return 0;
377}
284#endif 378#endif
diff --git a/include/sound/soc.h b/include/sound/soc.h
index e52a2fae146..1f661a760ae 100644
--- a/include/sound/soc.h
+++ b/include/sound/soc.h
@@ -247,6 +247,7 @@ struct snd_soc_jack;
247struct snd_soc_jack_zone; 247struct snd_soc_jack_zone;
248struct snd_soc_jack_pin; 248struct snd_soc_jack_pin;
249struct snd_soc_cache_ops; 249struct snd_soc_cache_ops;
250struct snd_soc_dsp_link;
250#include <sound/soc-dapm.h> 251#include <sound/soc-dapm.h>
251 252
252#ifdef CONFIG_GPIOLIB 253#ifdef CONFIG_GPIOLIB
@@ -317,6 +318,11 @@ int snd_soc_platform_read(struct snd_soc_platform *platform,
317int snd_soc_platform_write(struct snd_soc_platform *platform, 318int snd_soc_platform_write(struct snd_soc_platform *platform,
318 unsigned int reg, unsigned int val); 319 unsigned int reg, unsigned int val);
319 320
321struct snd_pcm_substream *snd_soc_get_dai_substream(struct snd_soc_card *card,
322 const char *dai_link, int stream);
323struct snd_soc_pcm_runtime *snd_soc_get_pcm_runtime(struct snd_soc_card *card,
324 const char *dai_link);
325
320/* Utility functions to get clock rates from various things */ 326/* Utility functions to get clock rates from various things */
321int snd_soc_calc_frame_size(int sample_size, int channels, int tdm_slots); 327int snd_soc_calc_frame_size(int sample_size, int channels, int tdm_slots);
322int snd_soc_params_to_frame_size(struct snd_pcm_hw_params *params); 328int snd_soc_params_to_frame_size(struct snd_pcm_hw_params *params);
@@ -701,15 +707,29 @@ struct snd_soc_dai_link {
701 const char *cpu_dai_name; 707 const char *cpu_dai_name;
702 const char *codec_dai_name; 708 const char *codec_dai_name;
703 709
710 struct snd_soc_dsp_link *dsp_link;
711
704 /* Keep DAI active over suspend */ 712 /* Keep DAI active over suspend */
705 unsigned int ignore_suspend:1; 713 unsigned int ignore_suspend:1;
706 714
707 /* Symmetry requirements */ 715 /* Symmetry requirements */
708 unsigned int symmetric_rates:1; 716 unsigned int symmetric_rates:1;
717 /* No PCM created for this DAI link */
718 unsigned int no_pcm:1;
719 /* This DAI link can change CODEC and platform at runtime*/
720 unsigned int dynamic:1;
721 /* This DAI link has no codec side driver*/
722 unsigned int no_codec:1;
723 /* This DAI has a Backend ID */
724 unsigned int be_id;
709 725
710 /* codec/machine specific init - e.g. add machine controls */ 726 /* codec/machine specific init - e.g. add machine controls */
711 int (*init)(struct snd_soc_pcm_runtime *rtd); 727 int (*init)(struct snd_soc_pcm_runtime *rtd);
712 728
729 /* hw_params re-writing for BE and FE sync */
730 int (*be_hw_params_fixup)(struct snd_soc_pcm_runtime *rtd,
731 struct snd_pcm_hw_params *params);
732
713 /* machine stream operations */ 733 /* machine stream operations */
714 struct snd_soc_ops *ops; 734 struct snd_soc_ops *ops;
715}; 735};
@@ -749,6 +769,7 @@ struct snd_soc_card {
749 769
750 struct list_head list; 770 struct list_head list;
751 struct mutex mutex; 771 struct mutex mutex;
772 struct mutex dsp_mutex;
752 773
753 bool instantiated; 774 bool instantiated;
754 775
@@ -826,6 +847,16 @@ struct snd_soc_card {
826 void *drvdata; 847 void *drvdata;
827}; 848};
828 849
850/* DSP runtime data */
851struct snd_soc_dsp_runtime {
852 struct list_head be_clients;
853 struct list_head fe_clients;
854 int users;
855 struct snd_pcm_runtime *runtime;
856 struct snd_pcm_hw_params params;
857 int runtime_update;
858};
859
829/* SoC machine DAI configuration, glues a codec and cpu DAI together */ 860/* SoC machine DAI configuration, glues a codec and cpu DAI together */
830struct snd_soc_pcm_runtime { 861struct snd_soc_pcm_runtime {
831 struct device dev; 862 struct device dev;
@@ -838,6 +869,9 @@ struct snd_soc_pcm_runtime {
838 unsigned int complete:1; 869 unsigned int complete:1;
839 unsigned int dev_registered:1; 870 unsigned int dev_registered:1;
840 871
872 /* DSP runtime data */
873 struct snd_soc_dsp_runtime dsp[2];
874
841 /* Symmetry data - only valid if symmetry is being enforced */ 875 /* Symmetry data - only valid if symmetry is being enforced */
842 unsigned int rate; 876 unsigned int rate;
843 long pmdown_time; 877 long pmdown_time;
@@ -850,6 +884,10 @@ struct snd_soc_pcm_runtime {
850 struct snd_soc_dai *cpu_dai; 884 struct snd_soc_dai *cpu_dai;
851 885
852 struct delayed_work delayed_work; 886 struct delayed_work delayed_work;
887
888#ifdef CONFIG_DEBUG_FS
889 struct dentry *debugfs_dsp_root;
890#endif
853}; 891};
854 892
855/* mixer control */ 893/* mixer control */
diff --git a/sound/soc/soc-core.c b/sound/soc/soc-core.c
index 726d24076e8..b46b8178eb6 100644
--- a/sound/soc/soc-core.c
+++ b/sound/soc/soc-core.c
@@ -782,7 +782,7 @@ find_codec:
782 782
783 /* CODEC found, so find CODEC DAI from registered DAIs from this CODEC*/ 783 /* CODEC found, so find CODEC DAI from registered DAIs from this CODEC*/
784 list_for_each_entry(codec_dai, &dai_list, list) { 784 list_for_each_entry(codec_dai, &dai_list, list) {
785 if (codec->dev == codec_dai->dev && 785 if ((codec->dev == codec_dai->dev || codec->driver == &null_codec_drv) &&
786 !strcmp(codec_dai->name, dai_link->codec_dai_name)) { 786 !strcmp(codec_dai->name, dai_link->codec_dai_name)) {
787 rtd->codec_dai = codec_dai; 787 rtd->codec_dai = codec_dai;
788 goto find_platform; 788 goto find_platform;