Lines Matching +full:is +full:- +full:compress +full:- +full:dai
1 // SPDX-License-Identifier: GPL-2.0+
3 // soc-compress.c -- ALSA SoC Compress
21 #include <sound/soc-dpcm.h>
22 #include <sound/soc-link.h>
28 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_components_open()
33 if (!component->driver->compress_ops || in soc_compr_components_open()
34 !component->driver->compress_ops->open) in soc_compr_components_open()
37 ret = component->driver->compress_ops->open(component, cstream); in soc_compr_components_open()
39 dev_err(component->dev, in soc_compr_components_open()
40 "Compress ASoC: can't open platform %s: %d\n", in soc_compr_components_open()
41 component->name, ret); in soc_compr_components_open()
55 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_components_free()
63 if (!component->driver->compress_ops || in soc_compr_components_free()
64 !component->driver->compress_ops->free) in soc_compr_components_free()
67 component->driver->compress_ops->free(component, cstream); in soc_compr_components_free()
75 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_open()
84 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_open()
98 snd_soc_runtime_activate(rtd, cstream->direction); in soc_compr_open()
100 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_open()
109 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_open()
118 struct snd_soc_pcm_runtime *fe = cstream->private_data; in soc_compr_open_fe()
120 fe->pcm->streams[cstream->direction].substream; in soc_compr_open_fe()
128 if (cstream->direction == SND_COMPRESS_PLAYBACK) in soc_compr_open_fe()
133 mutex_lock_nested(&fe->card->mutex, SND_SOC_CARD_CLASS_RUNTIME); in soc_compr_open_fe()
134 fe->dpcm[stream].runtime = fe_substream->runtime; in soc_compr_open_fe()
140 dev_dbg(fe->dev, "Compress ASoC: %s no valid %s route\n", in soc_compr_open_fe()
141 fe->dai_link->name, stream ? "capture" : "playback"); in soc_compr_open_fe()
142 /* calculate valid and active FE <-> BE dpcms */ in soc_compr_open_fe()
144 fe->dpcm[stream].runtime = fe_substream->runtime; in soc_compr_open_fe()
146 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_FE; in soc_compr_open_fe()
152 dpcm->state = SND_SOC_DPCM_LINK_STATE_FREE; in soc_compr_open_fe()
155 fe->dpcm[stream].runtime = NULL; in soc_compr_open_fe()
174 fe->dpcm[stream].state = SND_SOC_DPCM_STATE_OPEN; in soc_compr_open_fe()
175 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_NO; in soc_compr_open_fe()
179 mutex_unlock(&fe->card->mutex); in soc_compr_open_fe()
190 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_NO; in soc_compr_open_fe()
191 mutex_unlock(&fe->card->mutex); in soc_compr_open_fe()
197 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_free()
202 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_free()
204 if (cstream->direction == SND_COMPRESS_PLAYBACK) in soc_compr_free()
211 snd_soc_dai_digital_mute(codec_dai, 1, cstream->direction); in soc_compr_free()
214 cpu_dai->rate = 0; in soc_compr_free()
217 codec_dai->rate = 0; in soc_compr_free()
227 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_free()
236 struct snd_soc_pcm_runtime *fe = cstream->private_data; in soc_compr_free_fe()
241 mutex_lock_nested(&fe->card->mutex, SND_SOC_CARD_CLASS_RUNTIME); in soc_compr_free_fe()
243 if (cstream->direction == SND_COMPRESS_PLAYBACK) in soc_compr_free_fe()
250 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_FE; in soc_compr_free_fe()
254 dev_err(fe->dev, "Compressed ASoC: hw_free failed: %d\n", ret); in soc_compr_free_fe()
260 dpcm->state = SND_SOC_DPCM_LINK_STATE_FREE; in soc_compr_free_fe()
264 fe->dpcm[stream].state = SND_SOC_DPCM_STATE_CLOSE; in soc_compr_free_fe()
265 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_NO; in soc_compr_free_fe()
269 fe->dpcm[stream].runtime = NULL; in soc_compr_free_fe()
277 mutex_unlock(&fe->card->mutex); in soc_compr_free_fe()
284 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_components_trigger()
289 if (!component->driver->compress_ops || in soc_compr_components_trigger()
290 !component->driver->compress_ops->trigger) in soc_compr_components_trigger()
293 ret = component->driver->compress_ops->trigger( in soc_compr_components_trigger()
304 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_trigger()
309 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_trigger()
321 snd_soc_dai_digital_mute(codec_dai, 0, cstream->direction); in soc_compr_trigger()
324 snd_soc_dai_digital_mute(codec_dai, 1, cstream->direction); in soc_compr_trigger()
329 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_trigger()
335 struct snd_soc_pcm_runtime *fe = cstream->private_data; in soc_compr_trigger_fe()
343 if (cstream->direction == SND_COMPRESS_PLAYBACK) in soc_compr_trigger_fe()
348 mutex_lock_nested(&fe->card->mutex, SND_SOC_CARD_CLASS_RUNTIME); in soc_compr_trigger_fe()
358 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_FE; in soc_compr_trigger_fe()
366 fe->dpcm[stream].state = SND_SOC_DPCM_STATE_START; in soc_compr_trigger_fe()
370 fe->dpcm[stream].state = SND_SOC_DPCM_STATE_STOP; in soc_compr_trigger_fe()
373 fe->dpcm[stream].state = SND_SOC_DPCM_STATE_PAUSED; in soc_compr_trigger_fe()
378 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_NO; in soc_compr_trigger_fe()
379 mutex_unlock(&fe->card->mutex); in soc_compr_trigger_fe()
386 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_components_set_params()
391 if (!component->driver->compress_ops || in soc_compr_components_set_params()
392 !component->driver->compress_ops->set_params) in soc_compr_components_set_params()
395 ret = component->driver->compress_ops->set_params( in soc_compr_components_set_params()
407 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_set_params()
411 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_set_params()
414 * First we call set_params for the CPU DAI, then the component in soc_compr_set_params()
416 * compressed ops then we call that as well. The expectation is in soc_compr_set_params()
417 * that these callbacks will configure everything for this compress in soc_compr_set_params()
432 if (cstream->direction == SND_COMPRESS_PLAYBACK) in soc_compr_set_params()
439 /* cancel any delayed stream shutdown that is pending */ in soc_compr_set_params()
440 rtd->pop_wait = 0; in soc_compr_set_params()
441 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_set_params()
443 cancel_delayed_work_sync(&rtd->delayed_work); in soc_compr_set_params()
448 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_set_params()
455 struct snd_soc_pcm_runtime *fe = cstream->private_data; in soc_compr_set_params_fe()
457 fe->pcm->streams[cstream->direction].substream; in soc_compr_set_params_fe()
461 if (cstream->direction == SND_COMPRESS_PLAYBACK) in soc_compr_set_params_fe()
466 mutex_lock_nested(&fe->card->mutex, SND_SOC_CARD_CLASS_RUNTIME); in soc_compr_set_params_fe()
471 * I.e. machine driver fixup for compressed BE is mandatory. in soc_compr_set_params_fe()
473 memset(&fe->dpcm[fe_substream->stream].hw_params, 0, in soc_compr_set_params_fe()
476 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_FE; in soc_compr_set_params_fe()
499 fe->dpcm[stream].state = SND_SOC_DPCM_STATE_PREPARE; in soc_compr_set_params_fe()
502 fe->dpcm[stream].runtime_update = SND_SOC_DPCM_UPDATE_NO; in soc_compr_set_params_fe()
503 mutex_unlock(&fe->card->mutex); in soc_compr_set_params_fe()
510 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_get_params()
515 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_get_params()
522 if (!component->driver->compress_ops || in soc_compr_get_params()
523 !component->driver->compress_ops->get_params) in soc_compr_get_params()
526 ret = component->driver->compress_ops->get_params( in soc_compr_get_params()
532 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_get_params()
539 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_get_caps()
543 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_get_caps()
546 if (!component->driver->compress_ops || in soc_compr_get_caps()
547 !component->driver->compress_ops->get_caps) in soc_compr_get_caps()
550 ret = component->driver->compress_ops->get_caps( in soc_compr_get_caps()
555 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_get_caps()
562 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_get_codec_caps()
566 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_get_codec_caps()
569 if (!component->driver->compress_ops || in soc_compr_get_codec_caps()
570 !component->driver->compress_ops->get_codec_caps) in soc_compr_get_codec_caps()
573 ret = component->driver->compress_ops->get_codec_caps( in soc_compr_get_codec_caps()
578 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_get_codec_caps()
584 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_ack()
589 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_ack()
596 if (!component->driver->compress_ops || in soc_compr_ack()
597 !component->driver->compress_ops->ack) in soc_compr_ack()
600 ret = component->driver->compress_ops->ack( in soc_compr_ack()
607 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_ack()
614 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_pointer()
619 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_pointer()
626 if (!component->driver->compress_ops || in soc_compr_pointer()
627 !component->driver->compress_ops->pointer) in soc_compr_pointer()
630 ret = component->driver->compress_ops->pointer( in soc_compr_pointer()
635 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_pointer()
642 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_copy()
646 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass); in soc_compr_copy()
649 if (!component->driver->compress_ops || in soc_compr_copy()
650 !component->driver->compress_ops->copy) in soc_compr_copy()
653 ret = component->driver->compress_ops->copy( in soc_compr_copy()
658 mutex_unlock(&rtd->card->pcm_mutex); in soc_compr_copy()
665 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_set_metadata()
675 if (!component->driver->compress_ops || in soc_compr_set_metadata()
676 !component->driver->compress_ops->set_metadata) in soc_compr_set_metadata()
679 ret = component->driver->compress_ops->set_metadata( in soc_compr_set_metadata()
691 struct snd_soc_pcm_runtime *rtd = cstream->private_data; in soc_compr_get_metadata()
701 if (!component->driver->compress_ops || in soc_compr_get_metadata()
702 !component->driver->compress_ops->get_metadata) in soc_compr_get_metadata()
705 return component->driver->compress_ops->get_metadata( in soc_compr_get_metadata()
712 /* ASoC Compress operations */
727 /* ASoC Dynamic Compress operations */
743 * snd_soc_new_compress - create a new compress.
745 * @rtd: The runtime for which we will create compress
746 * @num: the device index number (zero based - shared with normal PCMs)
762 if (rtd->num_cpus > 1 || in snd_soc_new_compress()
763 rtd->num_codecs > 1) { in snd_soc_new_compress()
764 dev_err(rtd->card->dev, in snd_soc_new_compress()
765 "Compress ASoC: Multi CPU/Codec not supported\n"); in snd_soc_new_compress()
766 return -EINVAL; in snd_soc_new_compress()
770 dev_err(rtd->card->dev, "Missing codec\n"); in snd_soc_new_compress()
771 return -EINVAL; in snd_soc_new_compress()
783 * Compress devices are unidirectional so only one of the directions in snd_soc_new_compress()
787 dev_err(rtd->card->dev, in snd_soc_new_compress()
788 "Compress ASoC: Invalid direction for P %d, C %d\n", in snd_soc_new_compress()
790 return -EINVAL; in snd_soc_new_compress()
798 compr = devm_kzalloc(rtd->card->dev, sizeof(*compr), GFP_KERNEL); in snd_soc_new_compress()
800 return -ENOMEM; in snd_soc_new_compress()
802 compr->ops = devm_kzalloc(rtd->card->dev, sizeof(soc_compr_ops), in snd_soc_new_compress()
804 if (!compr->ops) in snd_soc_new_compress()
805 return -ENOMEM; in snd_soc_new_compress()
807 if (rtd->dai_link->dynamic) { in snd_soc_new_compress()
809 rtd->dai_link->stream_name); in snd_soc_new_compress()
811 ret = snd_pcm_new_internal(rtd->card->snd_card, new_name, num, in snd_soc_new_compress()
812 rtd->dai_link->dpcm_playback, in snd_soc_new_compress()
813 rtd->dai_link->dpcm_capture, &be_pcm); in snd_soc_new_compress()
815 dev_err(rtd->card->dev, in snd_soc_new_compress()
816 "Compress ASoC: can't create compressed for %s: %d\n", in snd_soc_new_compress()
817 rtd->dai_link->name, ret); in snd_soc_new_compress()
821 rtd->pcm = be_pcm; in snd_soc_new_compress()
822 rtd->fe_compr = 1; in snd_soc_new_compress()
823 if (rtd->dai_link->dpcm_playback) in snd_soc_new_compress()
824 be_pcm->streams[SNDRV_PCM_STREAM_PLAYBACK].substream->private_data = rtd; in snd_soc_new_compress()
825 if (rtd->dai_link->dpcm_capture) in snd_soc_new_compress()
826 be_pcm->streams[SNDRV_PCM_STREAM_CAPTURE].substream->private_data = rtd; in snd_soc_new_compress()
827 memcpy(compr->ops, &soc_compr_dyn_ops, sizeof(soc_compr_dyn_ops)); in snd_soc_new_compress()
829 snprintf(new_name, sizeof(new_name), "%s %s-%d", in snd_soc_new_compress()
830 rtd->dai_link->stream_name, codec_dai->name, num); in snd_soc_new_compress()
832 memcpy(compr->ops, &soc_compr_ops, sizeof(soc_compr_ops)); in snd_soc_new_compress()
836 if (!component->driver->compress_ops || in snd_soc_new_compress()
837 !component->driver->compress_ops->copy) in snd_soc_new_compress()
840 compr->ops->copy = soc_compr_copy; in snd_soc_new_compress()
844 mutex_init(&compr->lock); in snd_soc_new_compress()
845 ret = snd_compress_new(rtd->card->snd_card, num, direction, in snd_soc_new_compress()
848 component = asoc_rtd_to_codec(rtd, 0)->component; in snd_soc_new_compress()
849 dev_err(component->dev, in snd_soc_new_compress()
850 "Compress ASoC: can't create compress for codec %s: %d\n", in snd_soc_new_compress()
851 component->name, ret); in snd_soc_new_compress()
855 /* DAPM dai link stream work */ in snd_soc_new_compress()
856 rtd->close_delayed_work_func = snd_soc_close_delayed_work; in snd_soc_new_compress()
858 rtd->compr = compr; in snd_soc_new_compress()
859 compr->private_data = rtd; in snd_soc_new_compress()
861 dev_dbg(rtd->card->dev, "Compress ASoC: %s <-> %s mapping ok\n", in snd_soc_new_compress()
862 codec_dai->name, cpu_dai->name); in snd_soc_new_compress()