diff options
author | Mark Brown <broonie@kernel.org> | 2020-11-16 23:28:03 +0000 |
---|---|---|
committer | Mark Brown <broonie@kernel.org> | 2020-11-16 23:28:03 +0000 |
commit | 4fb87241e5192caf9226fd4ca96ce2fd861503c1 (patch) | |
tree | 21e6cc146f372f5d60edc49c36b2ece7a61c7f7d /sound/soc/intel/catpt/pcm.c | |
parent | 47f667afe716113ace014691bfdc134ce9045d18 (diff) | |
parent | 3d32489838bbf3119bb1ea59cdbed0077d7dbf3c (diff) |
Merge series "ASoC: Intel: catpt: Offload fixes and code optimization" from Cezary Rojewski <cezary.rojewski@intel.com>:
First two of the series address bugs connected mainly to offload streams:
- scenarios with very low buffer sizes: RESET_STREAM IPC timeouts
- fix lp clock selection when switching between PAUSE <-> RESUME states:
glitches on first offload when no additional stream is opened
simultaneously
Follow ups are: code reduction and optimization oriented patches.
This has been foretold in:
[PATCH v10 00/14] ASoC: Intel: Catpt - Lynx and Wildcat point
https://www.spinics.net/lists/alsa-devel/msg116440.html
Note: LPT power up/down sequences might get aligned with WPT once
enough testing is done as capabilities are shared for both DSPs.
First, optimize applying of user settings - prevent redundand calls from
happening - and then as mentioned above, streamline power on/off sequence
for LPT and WPT.
Cezary Rojewski (5):
ASoC: Intel: catpt: Skip position update for unprepared streams
ASoC: Intel: catpt: Correct clock selection for dai trigger
ASoC: Intel: catpt: Optimize applying user settings
ASoC: Intel: catpt: Streamline power routines across LPT and WPT
ASoC: Intel: catpt: Cleanup after power routines streamlining
sound/soc/intel/catpt/core.h | 10 ++-
sound/soc/intel/catpt/device.c | 18 +++---
sound/soc/intel/catpt/dsp.c | 56 ++--------------
sound/soc/intel/catpt/pcm.c | 113 ++++++++++++++++-----------------
4 files changed, 74 insertions(+), 123 deletions(-)
--
2.17.1
base-commit: 3650b228f83adda7e5ee532e2b90429c03f7b9ec
Diffstat (limited to 'sound/soc/intel/catpt/pcm.c')
-rw-r--r-- | sound/soc/intel/catpt/pcm.c | 113 |
1 files changed, 56 insertions, 57 deletions
diff --git a/sound/soc/intel/catpt/pcm.c b/sound/soc/intel/catpt/pcm.c index 1775540ac92b..e5d54bb1c42a 100644 --- a/sound/soc/intel/catpt/pcm.c +++ b/sound/soc/intel/catpt/pcm.c @@ -324,6 +324,54 @@ static void catpt_dai_shutdown(struct snd_pcm_substream *substream, snd_soc_dai_set_dma_data(dai, substream, NULL); } +static int catpt_set_dspvol(struct catpt_dev *cdev, u8 stream_id, long *ctlvol); + +static int catpt_dai_apply_usettings(struct snd_soc_dai *dai, + struct catpt_stream_runtime *stream) +{ + struct catpt_dev *cdev = dev_get_drvdata(dai->dev); + struct snd_soc_component *component = dai->component; + struct snd_kcontrol *pos, *kctl = NULL; + const char *name; + int ret; + u32 id = stream->info.stream_hw_id; + + /* only selected streams have individual controls */ + switch (id) { + case CATPT_PIN_ID_OFFLOAD1: + name = "Media0 Playback Volume"; + break; + case CATPT_PIN_ID_OFFLOAD2: + name = "Media1 Playback Volume"; + break; + case CATPT_PIN_ID_CAPTURE1: + name = "Mic Capture Volume"; + break; + case CATPT_PIN_ID_REFERENCE: + name = "Loopback Mute"; + break; + default: + return 0; + }; + + list_for_each_entry(pos, &component->card->snd_card->controls, list) { + if (pos->private_data == component && + !strncmp(name, pos->id.name, sizeof(pos->id.name))) { + kctl = pos; + break; + } + } + if (!kctl) + return -ENOENT; + + if (stream->template->type != CATPT_STRM_TYPE_LOOPBACK) + return catpt_set_dspvol(cdev, id, (long *)kctl->private_value); + ret = catpt_ipc_mute_loopback(cdev, id, *(bool *)kctl->private_value); + if (ret) + return CATPT_IPC_ERROR(ret); + return 0; +} + static int catpt_dai_hw_params(struct snd_pcm_substream *substream, struct snd_pcm_hw_params *params, struct snd_soc_dai *dai) @@ -370,6 +418,10 @@ static int catpt_dai_hw_params(struct snd_pcm_substream *substream, if (ret) return CATPT_IPC_ERROR(ret); + ret = catpt_dai_apply_usettings(dai, stream); + if (ret) + return ret; + stream->allocated = true; return 0; } @@ -391,54 +443,6 @@ static int catpt_dai_hw_free(struct snd_pcm_substream *substream, return 0; } -static int catpt_set_dspvol(struct catpt_dev *cdev, u8 stream_id, long *ctlvol); - -static int catpt_dai_apply_usettings(struct snd_soc_dai *dai, - struct catpt_stream_runtime *stream) -{ - struct catpt_dev *cdev = dev_get_drvdata(dai->dev); - struct snd_soc_component *component = dai->component; - struct snd_kcontrol *pos, *kctl = NULL; - const char *name; - int ret; - u32 id = stream->info.stream_hw_id; - - /* only selected streams have individual controls */ - switch (id) { - case CATPT_PIN_ID_OFFLOAD1: - name = "Media0 Playback Volume"; - break; - case CATPT_PIN_ID_OFFLOAD2: - name = "Media1 Playback Volume"; - break; - case CATPT_PIN_ID_CAPTURE1: - name = "Mic Capture Volume"; - break; - case CATPT_PIN_ID_REFERENCE: - name = "Loopback Mute"; - break; - default: - return 0; - } - - list_for_each_entry(pos, &component->card->snd_card->controls, list) { - if (pos->private_data == component && - !strncmp(name, pos->id.name, sizeof(pos->id.name))) { - kctl = pos; - break; - } - } - if (!kctl) - return -ENOENT; - - if (stream->template->type != CATPT_STRM_TYPE_LOOPBACK) - return catpt_set_dspvol(cdev, id, (long *)kctl->private_value); - ret = catpt_ipc_mute_loopback(cdev, id, *(bool *)kctl->private_value); - if (ret) - return CATPT_IPC_ERROR(ret); - return 0; -} - static int catpt_dai_prepare(struct snd_pcm_substream *substream, struct snd_soc_dai *dai) { @@ -458,14 +462,6 @@ static int catpt_dai_prepare(struct snd_pcm_substream *substream, if (ret) return CATPT_IPC_ERROR(ret); - ret = catpt_dsp_update_lpclock(cdev); - if (ret) - return ret; - - ret = catpt_dai_apply_usettings(dai, stream); - if (ret) - return ret; - stream->prepared = true; return 0; } @@ -500,6 +496,7 @@ static int catpt_dai_trigger(struct snd_pcm_substream *substream, int cmd, case SNDRV_PCM_TRIGGER_RESUME: case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: resume_stream: + catpt_dsp_update_lpclock(cdev); ret = catpt_ipc_resume_stream(cdev, stream->info.stream_hw_id); if (ret) return CATPT_IPC_ERROR(ret); @@ -507,11 +504,11 @@ static int catpt_dai_trigger(struct snd_pcm_substream *substream, int cmd, case SNDRV_PCM_TRIGGER_STOP: stream->prepared = false; - catpt_dsp_update_lpclock(cdev); fallthrough; case SNDRV_PCM_TRIGGER_SUSPEND: case SNDRV_PCM_TRIGGER_PAUSE_PUSH: ret = catpt_ipc_pause_stream(cdev, stream->info.stream_hw_id); + catpt_dsp_update_lpclock(cdev); if (ret) return CATPT_IPC_ERROR(ret); break; @@ -534,6 +531,8 @@ void catpt_stream_update_position(struct catpt_dev *cdev, dsppos = bytes_to_frames(r, pos->stream_position); + if (!stream->prepared) + goto exit; /* only offload is set_write_pos driven */ if (stream->template->type != CATPT_STRM_TYPE_RENDER) goto exit; |