summaryrefslogtreecommitdiffstats
path: root/sound/soc/mediatek/common
diff options
context:
space:
mode:
Diffstat (limited to 'sound/soc/mediatek/common')
-rw-r--r--sound/soc/mediatek/common/mtk-afe-fe-dai.c22
-rw-r--r--sound/soc/mediatek/common/mtk-afe-platform-driver.c4
-rw-r--r--sound/soc/mediatek/common/mtk-dsp-sof-common.c113
-rw-r--r--sound/soc/mediatek/common/mtk-dsp-sof-common.h8
4 files changed, 119 insertions, 28 deletions
diff --git a/sound/soc/mediatek/common/mtk-afe-fe-dai.c b/sound/soc/mediatek/common/mtk-afe-fe-dai.c
index 395be97f13..3044d9ab3d 100644
--- a/sound/soc/mediatek/common/mtk-afe-fe-dai.c
+++ b/sound/soc/mediatek/common/mtk-afe-fe-dai.c
@@ -37,10 +37,10 @@ static int mtk_regmap_write(struct regmap *map, int reg, unsigned int val)
int mtk_afe_fe_startup(struct snd_pcm_substream *substream,
struct snd_soc_dai *dai)
{
- struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
+ struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct mtk_base_afe *afe = snd_soc_dai_get_drvdata(dai);
struct snd_pcm_runtime *runtime = substream->runtime;
- int memif_num = asoc_rtd_to_cpu(rtd, 0)->id;
+ int memif_num = snd_soc_rtd_to_cpu(rtd, 0)->id;
struct mtk_base_afe_memif *memif = &afe->memif[memif_num];
const struct snd_pcm_hardware *mtk_afe_hardware = afe->mtk_afe_hardware;
int ret;
@@ -98,9 +98,9 @@ EXPORT_SYMBOL_GPL(mtk_afe_fe_startup);
void mtk_afe_fe_shutdown(struct snd_pcm_substream *substream,
struct snd_soc_dai *dai)
{
- struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
+ struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct mtk_base_afe *afe = snd_soc_dai_get_drvdata(dai);
- struct mtk_base_afe_memif *memif = &afe->memif[asoc_rtd_to_cpu(rtd, 0)->id];
+ struct mtk_base_afe_memif *memif = &afe->memif[snd_soc_rtd_to_cpu(rtd, 0)->id];
int irq_id;
irq_id = memif->irq_usage;
@@ -120,9 +120,9 @@ int mtk_afe_fe_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *params,
struct snd_soc_dai *dai)
{
- struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
+ struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct mtk_base_afe *afe = snd_soc_dai_get_drvdata(dai);
- int id = asoc_rtd_to_cpu(rtd, 0)->id;
+ int id = snd_soc_rtd_to_cpu(rtd, 0)->id;
struct mtk_base_afe_memif *memif = &afe->memif[id];
int ret;
unsigned int channels = params_channels(params);
@@ -196,10 +196,10 @@ EXPORT_SYMBOL_GPL(mtk_afe_fe_hw_free);
int mtk_afe_fe_trigger(struct snd_pcm_substream *substream, int cmd,
struct snd_soc_dai *dai)
{
- struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
+ struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct snd_pcm_runtime * const runtime = substream->runtime;
struct mtk_base_afe *afe = snd_soc_dai_get_drvdata(dai);
- int id = asoc_rtd_to_cpu(rtd, 0)->id;
+ int id = snd_soc_rtd_to_cpu(rtd, 0)->id;
struct mtk_base_afe_memif *memif = &afe->memif[id];
struct mtk_base_afe_irq *irqs = &afe->irqs[memif->irq_usage];
const struct mtk_base_irq_data *irq_data = irqs->irq_data;
@@ -263,9 +263,9 @@ EXPORT_SYMBOL_GPL(mtk_afe_fe_trigger);
int mtk_afe_fe_prepare(struct snd_pcm_substream *substream,
struct snd_soc_dai *dai)
{
- struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
+ struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct mtk_base_afe *afe = snd_soc_dai_get_drvdata(dai);
- int id = asoc_rtd_to_cpu(rtd, 0)->id;
+ int id = snd_soc_rtd_to_cpu(rtd, 0)->id;
int pbuf_size;
if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
@@ -523,7 +523,7 @@ EXPORT_SYMBOL_GPL(mtk_memif_set_rate);
int mtk_memif_set_rate_substream(struct snd_pcm_substream *substream,
int id, unsigned int rate)
{
- struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
+ struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct snd_soc_component *component =
snd_soc_rtdcom_lookup(rtd, AFE_PCM_NAME);
struct mtk_base_afe *afe = snd_soc_component_get_drvdata(component);
diff --git a/sound/soc/mediatek/common/mtk-afe-platform-driver.c b/sound/soc/mediatek/common/mtk-afe-platform-driver.c
index 01501d5747..32edcb6d52 100644
--- a/sound/soc/mediatek/common/mtk-afe-platform-driver.c
+++ b/sound/soc/mediatek/common/mtk-afe-platform-driver.c
@@ -80,9 +80,9 @@ EXPORT_SYMBOL_GPL(mtk_afe_add_sub_dai_control);
snd_pcm_uframes_t mtk_afe_pcm_pointer(struct snd_soc_component *component,
struct snd_pcm_substream *substream)
{
- struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
+ struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct mtk_base_afe *afe = snd_soc_component_get_drvdata(component);
- struct mtk_base_afe_memif *memif = &afe->memif[asoc_rtd_to_cpu(rtd, 0)->id];
+ struct mtk_base_afe_memif *memif = &afe->memif[snd_soc_rtd_to_cpu(rtd, 0)->id];
const struct mtk_base_memif_data *memif_data = memif->data;
struct regmap *regmap = afe->regmap;
struct device *dev = afe->dev;
diff --git a/sound/soc/mediatek/common/mtk-dsp-sof-common.c b/sound/soc/mediatek/common/mtk-dsp-sof-common.c
index 21a9403b7e..7ec8965a70 100644
--- a/sound/soc/mediatek/common/mtk-dsp-sof-common.c
+++ b/sound/soc/mediatek/common/mtk-dsp-sof-common.c
@@ -54,6 +54,8 @@ int mtk_sof_card_probe(struct snd_soc_card *card)
{
int i;
struct snd_soc_dai_link *dai_link;
+ struct mtk_soc_card_data *soc_card_data = snd_soc_card_get_drvdata(card);
+ struct mtk_sof_priv *sof_priv = soc_card_data->sof_priv;
/* Set stream_name to help sof bind widgets */
for_each_card_prelinks(card, i, dai_link) {
@@ -61,10 +63,81 @@ int mtk_sof_card_probe(struct snd_soc_card *card)
dai_link->stream_name = dai_link->name;
}
+ INIT_LIST_HEAD(&sof_priv->dai_link_list);
+
return 0;
}
EXPORT_SYMBOL_GPL(mtk_sof_card_probe);
+static struct snd_soc_pcm_runtime *mtk_sof_find_tplg_be(struct snd_soc_pcm_runtime *rtd)
+{
+ struct snd_soc_card *card = rtd->card;
+ struct mtk_soc_card_data *soc_card_data = snd_soc_card_get_drvdata(card);
+ struct mtk_sof_priv *sof_priv = soc_card_data->sof_priv;
+ struct snd_soc_pcm_runtime *fe;
+ struct snd_soc_pcm_runtime *be;
+ struct snd_soc_dpcm *dpcm;
+ int i, stream;
+
+ for_each_pcm_streams(stream) {
+ fe = NULL;
+ for_each_dpcm_fe(rtd, stream, dpcm) {
+ fe = dpcm->fe;
+ if (fe)
+ break;
+ }
+
+ if (!fe)
+ continue;
+
+ for_each_dpcm_be(fe, stream, dpcm) {
+ be = dpcm->be;
+ if (be == rtd)
+ continue;
+
+ for (i = 0; i < sof_priv->num_streams; i++) {
+ const struct sof_conn_stream *conn = &sof_priv->conn_streams[i];
+
+ if (!strcmp(be->dai_link->name, conn->sof_link))
+ return be;
+ }
+ }
+ }
+
+ return NULL;
+}
+
+/* fixup the BE DAI link to match any values from topology */
+static int mtk_sof_check_tplg_be_dai_link_fixup(struct snd_soc_pcm_runtime *rtd,
+ struct snd_pcm_hw_params *params)
+{
+ struct snd_soc_card *card = rtd->card;
+ struct mtk_soc_card_data *soc_card_data = snd_soc_card_get_drvdata(card);
+ struct mtk_sof_priv *sof_priv = soc_card_data->sof_priv;
+ struct snd_soc_pcm_runtime *sof_be;
+ struct mtk_dai_link *dai_link;
+ int ret = 0;
+
+ sof_be = mtk_sof_find_tplg_be(rtd);
+ if (sof_be) {
+ if (sof_priv->sof_dai_link_fixup)
+ ret = sof_priv->sof_dai_link_fixup(rtd, params);
+ else if (sof_be->dai_link->be_hw_params_fixup)
+ ret = sof_be->dai_link->be_hw_params_fixup(sof_be, params);
+ } else {
+ list_for_each_entry(dai_link, &sof_priv->dai_link_list, list) {
+ if (strcmp(dai_link->name, rtd->dai_link->name) == 0) {
+ if (dai_link->be_hw_params_fixup)
+ ret = dai_link->be_hw_params_fixup(rtd, params);
+
+ break;
+ }
+ }
+ }
+
+ return ret;
+}
+
int mtk_sof_card_late_probe(struct snd_soc_card *card)
{
struct snd_soc_pcm_runtime *rtd;
@@ -72,6 +145,8 @@ int mtk_sof_card_late_probe(struct snd_soc_card *card)
struct mtk_soc_card_data *soc_card_data =
snd_soc_card_get_drvdata(card);
struct mtk_sof_priv *sof_priv = soc_card_data->sof_priv;
+ struct snd_soc_dai_link *dai_link;
+ struct mtk_dai_link *mtk_dai_link;
int i;
/* 1. find sof component */
@@ -86,25 +161,37 @@ int mtk_sof_card_late_probe(struct snd_soc_card *card)
return 0;
}
- /* 2. add route path and fixup callback */
+ /* 2. overwrite all BE fixups, and backup the existing fixup */
+ for_each_card_prelinks(card, i, dai_link) {
+ if (dai_link->be_hw_params_fixup) {
+ mtk_dai_link = devm_kzalloc(card->dev,
+ sizeof(*mtk_dai_link),
+ GFP_KERNEL);
+ if (!mtk_dai_link)
+ return -ENOMEM;
+
+ mtk_dai_link->be_hw_params_fixup = dai_link->be_hw_params_fixup;
+ mtk_dai_link->name = dai_link->name;
+
+ list_add(&mtk_dai_link->list, &sof_priv->dai_link_list);
+ }
+
+ if (dai_link->no_pcm)
+ dai_link->be_hw_params_fixup = mtk_sof_check_tplg_be_dai_link_fixup;
+ }
+
+ /* 3. add route path and SOF_BE fixup callback */
for (i = 0; i < sof_priv->num_streams; i++) {
const struct sof_conn_stream *conn = &sof_priv->conn_streams[i];
struct snd_soc_pcm_runtime *sof_rtd = NULL;
- struct snd_soc_pcm_runtime *normal_rtd = NULL;
for_each_card_rtds(card, rtd) {
if (!strcmp(rtd->dai_link->name, conn->sof_link)) {
sof_rtd = rtd;
- continue;
- }
- if (!strcmp(rtd->dai_link->name, conn->normal_link)) {
- normal_rtd = rtd;
- continue;
- }
- if (normal_rtd && sof_rtd)
break;
+ }
}
- if (normal_rtd && sof_rtd) {
+ if (sof_rtd) {
int j;
struct snd_soc_dai *cpu_dai;
@@ -131,13 +218,9 @@ int mtk_sof_card_late_probe(struct snd_soc_card *card)
}
}
+ /* overwrite SOF BE fixup */
sof_rtd->dai_link->be_hw_params_fixup =
sof_comp->driver->be_hw_params_fixup;
- if (sof_priv->sof_dai_link_fixup)
- normal_rtd->dai_link->be_hw_params_fixup =
- sof_priv->sof_dai_link_fixup;
- else
- normal_rtd->dai_link->be_hw_params_fixup = mtk_sof_dai_link_fixup;
}
}
diff --git a/sound/soc/mediatek/common/mtk-dsp-sof-common.h b/sound/soc/mediatek/common/mtk-dsp-sof-common.h
index dd38c4a935..4bc5e1c0c8 100644
--- a/sound/soc/mediatek/common/mtk-dsp-sof-common.h
+++ b/sound/soc/mediatek/common/mtk-dsp-sof-common.h
@@ -18,11 +18,19 @@ struct sof_conn_stream {
int stream_dir;
};
+struct mtk_dai_link {
+ const char *name;
+ int (*be_hw_params_fixup)(struct snd_soc_pcm_runtime *rtd,
+ struct snd_pcm_hw_params *params);
+ struct list_head list;
+};
+
struct mtk_sof_priv {
const struct sof_conn_stream *conn_streams;
int num_streams;
int (*sof_dai_link_fixup)(struct snd_soc_pcm_runtime *rtd,
struct snd_pcm_hw_params *params);
+ struct list_head dai_link_list;
};
int mtk_sof_dai_link_fixup(struct snd_soc_pcm_runtime *rtd,