summaryrefslogtreecommitdiffstats
path: root/sound/soc/dwc
diff options
context:
space:
mode:
authorMaruthi Srinivas Bayyavarapu <Maruthi.Bayyavarapu@amd.com>2015-10-23 17:15:41 -0400
committerMark Brown <broonie@kernel.org>2015-10-24 06:29:38 +0900
commitab57b8e90c658a72944c48a81a1352e61e84db02 (patch)
tree3e425eb46f1fe598c204bcca88a98d08c713ad9d /sound/soc/dwc
parent1d957d862ac782eaf5803d4d4cf167708e4dc147 (diff)
downloadlinux-stable-ab57b8e90c658a72944c48a81a1352e61e84db02.tar.gz
linux-stable-ab57b8e90c658a72944c48a81a1352e61e84db02.tar.bz2
linux-stable-ab57b8e90c658a72944c48a81a1352e61e84db02.zip
ASoC: dwc: add check for master/slave format
DW i2s controller's master/slave config can be read from a read-only register. Machine driver can try to set a master/slave format on cpu-dai using 'set_fmt' of dai ops. A check is added to verify codec is master when dwc is slave and vice-versa. Signed-off-by: Maruthi Bayyavarapu <maruthi.bayyavarapu@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com> Signed-off-by: Mark Brown <broonie@kernel.org>
Diffstat (limited to 'sound/soc/dwc')
-rw-r--r--sound/soc/dwc/designware_i2s.c31
1 files changed, 31 insertions, 0 deletions
diff --git a/sound/soc/dwc/designware_i2s.c b/sound/soc/dwc/designware_i2s.c
index 3a52f82b5523..f427325ae448 100644
--- a/sound/soc/dwc/designware_i2s.c
+++ b/sound/soc/dwc/designware_i2s.c
@@ -341,12 +341,43 @@ static int dw_i2s_trigger(struct snd_pcm_substream *substream,
return ret;
}
+static int dw_i2s_set_fmt(struct snd_soc_dai *cpu_dai, unsigned int fmt)
+{
+ struct dw_i2s_dev *dev = snd_soc_dai_get_drvdata(cpu_dai);
+ int ret = 0;
+
+ switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) {
+ case SND_SOC_DAIFMT_CBM_CFM:
+ if (dev->capability & DW_I2S_SLAVE)
+ ret = 0;
+ else
+ ret = -EINVAL;
+ break;
+ case SND_SOC_DAIFMT_CBS_CFS:
+ if (dev->capability & DW_I2S_MASTER)
+ ret = 0;
+ else
+ ret = -EINVAL;
+ break;
+ case SND_SOC_DAIFMT_CBM_CFS:
+ case SND_SOC_DAIFMT_CBS_CFM:
+ ret = -EINVAL;
+ break;
+ default:
+ dev_dbg(dev->dev, "dwc : Invalid master/slave format\n");
+ ret = -EINVAL;
+ break;
+ }
+ return ret;
+}
+
static struct snd_soc_dai_ops dw_i2s_dai_ops = {
.startup = dw_i2s_startup,
.shutdown = dw_i2s_shutdown,
.hw_params = dw_i2s_hw_params,
.prepare = dw_i2s_prepare,
.trigger = dw_i2s_trigger,
+ .set_fmt = dw_i2s_set_fmt,
};
static const struct snd_soc_component_driver dw_i2s_component = {