@@ -186,6 +186,29 @@ static void hda_codec_dai_set_stream(struct snd_sof_dev *sdev,
snd_soc_dai_set_stream(codec_dai, hstream, substream->stream);
}
+static unsigned int hda_calc_stream_format(struct snd_sof_dev *sdev,
+ struct snd_pcm_substream *substream,
+ struct snd_pcm_hw_params *params)
+{
+ struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
+ struct snd_soc_dai *codec_dai = asoc_rtd_to_codec(rtd, 0);
+ unsigned int link_bps;
+ unsigned int format_val;
+
+ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
+ link_bps = codec_dai->driver->playback.sig_bits;
+ else
+ link_bps = codec_dai->driver->capture.sig_bits;
+
+ format_val = snd_hdac_calc_stream_format(params_rate(params), params_channels(params),
+ params_format(params), link_bps, 0);
+
+ dev_dbg(sdev->dev, "format_val=%#x, rate=%d, ch=%d, format=%d\n", format_val,
+ params_rate(params), params_channels(params), params_format(params));
+
+ return format_val;
+}
+
static int hda_ipc4_pre_trigger(struct snd_sof_dev *sdev, struct snd_soc_dai *cpu_dai,
struct snd_pcm_substream *substream, int cmd)
{
@@ -320,6 +343,7 @@ static const struct hda_dai_widget_dma_ops hda_ipc4_dma_ops = {
.trigger = hda_trigger,
.post_trigger = hda_ipc4_post_trigger,
.codec_dai_set_stream = hda_codec_dai_set_stream,
+ .calc_stream_format = hda_calc_stream_format,
};
static const struct hda_dai_widget_dma_ops hda_ipc4_chain_dma_ops = {
@@ -330,6 +354,7 @@ static const struct hda_dai_widget_dma_ops hda_ipc4_chain_dma_ops = {
.reset_hext_stream = hda_reset_hext_stream,
.trigger = hda_trigger,
.codec_dai_set_stream = hda_codec_dai_set_stream,
+ .calc_stream_format = hda_calc_stream_format,
};
static int hda_ipc3_post_trigger(struct snd_sof_dev *sdev, struct snd_soc_dai *cpu_dai,
@@ -364,6 +389,7 @@ static const struct hda_dai_widget_dma_ops hda_ipc3_dma_ops = {
.trigger = hda_trigger,
.post_trigger = hda_ipc3_post_trigger,
.codec_dai_set_stream = hda_codec_dai_set_stream,
+ .calc_stream_format = hda_calc_stream_format,
};
static struct hdac_ext_stream *
@@ -391,6 +417,7 @@ static const struct hda_dai_widget_dma_ops hda_dspless_dma_ops = {
.get_hext_stream = hda_dspless_get_hext_stream,
.setup_hext_stream = hda_dspless_setup_hext_stream,
.codec_dai_set_stream = hda_codec_dai_set_stream,
+ .calc_stream_format = hda_calc_stream_format,
};
#endif
@@ -159,8 +159,6 @@ static int hda_link_dma_hw_params(struct snd_pcm_substream *substream,
struct hdac_ext_link *hlink;
struct snd_sof_dev *sdev;
struct hdac_bus *bus;
- unsigned int format_val;
- unsigned int link_bps;
int stream_tag;
if (!ops) {
@@ -195,22 +193,14 @@ static int hda_link_dma_hw_params(struct snd_pcm_substream *substream,
if (ops->codec_dai_set_stream)
ops->codec_dai_set_stream(sdev, substream, hstream);
- if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
- link_bps = codec_dai->driver->playback.sig_bits;
- else
- link_bps = codec_dai->driver->capture.sig_bits;
-
if (ops->reset_hext_stream)
ops->reset_hext_stream(sdev, hext_stream);
- format_val = snd_hdac_calc_stream_format(params_rate(params), params_channels(params),
- params_format(params), link_bps, 0);
+ if (ops->calc_stream_format && ops->setup_hext_stream) {
+ unsigned int format_val = ops->calc_stream_format(sdev, substream, params);
- dev_dbg(bus->dev, "format_val=%#x, rate=%d, ch=%d, format=%d\n", format_val,
- params_rate(params), params_channels(params), params_format(params));
-
- if (ops->setup_hext_stream)
ops->setup_hext_stream(sdev, hext_stream, format_val);
+ }
hext_stream->link_prepared = 1;
@@ -920,6 +920,8 @@ int hda_dsp_ipc4_load_library(struct snd_sof_dev *sdev,
* @trigger: Function pointer for DAI DMA trigger actions
* @post_trigger: Function pointer for DAI DMA post-trigger actions
* @codec_dai_set_stream: Function pointer to set codec-side stream information
+ * @calc_stream_format: Function pointer to determine stream format from hw_params and
+ * for HDaudio codec DAI from the .sig bits
*/
struct hda_dai_widget_dma_ops {
struct hdac_ext_stream *(*get_hext_stream)(struct snd_sof_dev *sdev,
@@ -942,6 +944,9 @@ struct hda_dai_widget_dma_ops {
void (*codec_dai_set_stream)(struct snd_sof_dev *sdev,
struct snd_pcm_substream *substream,
struct hdac_stream *hstream);
+ unsigned int (*calc_stream_format)(struct snd_sof_dev *sdev,
+ struct snd_pcm_substream *substream,
+ struct snd_pcm_hw_params *params);
};
const struct hda_dai_widget_dma_ops *