summaryrefslogtreecommitdiff
path: root/sound
diff options
context:
space:
mode:
authorNicolin Chen <b42378@freescale.com>2013-11-08 15:48:42 +0800
committerNicolin Chen <b42378@freescale.com>2013-11-13 10:25:18 +0800
commit3304539eeb4e7b3b43d2cac0a2239658a6bf0a0a (patch)
tree59e0823ac020fbd69db651ec59e04c8cf5b10c8c /sound
parenta2ade259b50c64d8fe699df5c567e297c801376c (diff)
ENGR00286961-2 ASoC: fsl_ssi: Move DC configuration to set_dai_tdm_slot()
DC indicates Frame Rate Divider. By setting it we can get a desired time slot numbers. Thus it should be more plausible to set DC in set_dai_tdm_slot() instead of hw_params(). Acked-by: Wang Shengjiu <b02247@freescale.com> Signed-off-by: Nicolin Chen <b42378@freescale.com>
Diffstat (limited to 'sound')
-rw-r--r--sound/soc/fsl/fsl_ssi.c31
1 files changed, 25 insertions, 6 deletions
diff --git a/sound/soc/fsl/fsl_ssi.c b/sound/soc/fsl/fsl_ssi.c
index a75043d4cc61..6d7ea1f1c402 100644
--- a/sound/soc/fsl/fsl_ssi.c
+++ b/sound/soc/fsl/fsl_ssi.c
@@ -461,7 +461,6 @@ static int fsl_ssi_hw_params(struct snd_pcm_substream *substream,
snd_pcm_format_width(params_format(hw_params));
u32 wl = CCSR_SSI_SxCCR_WL(sample_size);
int enabled = read_ssi(&ssi->scr) & CCSR_SSI_SCR_SSIEN;
- u32 dc = CCSR_SSI_SxCCR_DC(params_channels(hw_params));
int ret;
/*
@@ -491,13 +490,10 @@ static int fsl_ssi_hw_params(struct snd_pcm_substream *substream,
/* In synchronous mode, the SSI uses STCCR for capture */
if ((substream->stream == SNDRV_PCM_STREAM_PLAYBACK) ||
- ssi_private->cpu_dai_drv.symmetric_rates) {
+ ssi_private->cpu_dai_drv.symmetric_rates)
write_ssi_mask(&ssi->stccr, CCSR_SSI_SxCCR_WL_MASK, wl);
- write_ssi_mask(&ssi->stccr, CCSR_SSI_SxCCR_DC_MASK, dc);
- } else {
+ else
write_ssi_mask(&ssi->srccr, CCSR_SSI_SxCCR_WL_MASK, wl);
- write_ssi_mask(&ssi->srccr, CCSR_SSI_SxCCR_WL_MASK, dc);
- }
return 0;
}
@@ -743,6 +739,28 @@ static int fsl_ssi_set_dai_sysclk(struct snd_soc_dai *cpu_dai,
return 0;
}
+static int fsl_ssi_set_dai_tdm_slot(struct snd_soc_dai *cpu_dai, u32 tx_mask,
+ u32 rx_mask, int slots, int slot_width)
+{
+ struct fsl_ssi_private *ssi_private = snd_soc_dai_get_drvdata(cpu_dai);
+ struct ccsr_ssi __iomem *ssi = ssi_private->ssi;
+
+ write_ssi_mask(&ssi->stccr, CCSR_SSI_SxCCR_DC_MASK,
+ CCSR_SSI_SxCCR_DC(slots));
+ write_ssi_mask(&ssi->srccr, CCSR_SSI_SxCCR_DC_MASK,
+ CCSR_SSI_SxCCR_DC(slots));
+
+ /* The register SxMSKs need SSI to provide essential clock due to
+ * hardware design. So we here temporarily enable SSI to set them.
+ */
+ write_ssi_mask(&ssi->scr, 0, CCSR_SSI_SCR_SSIEN);
+ write_ssi(tx_mask, &ssi->stmsk);
+ write_ssi(rx_mask, &ssi->srmsk);
+ write_ssi_mask(&ssi->scr, CCSR_SSI_SCR_SSIEN, 0);
+
+ return 0;
+}
+
/**
* fsl_ssi_shutdown: shutdown the SSI
*
@@ -793,6 +811,7 @@ static const struct snd_soc_dai_ops fsl_ssi_dai_ops = {
.hw_params = fsl_ssi_hw_params,
.set_fmt = fsl_ssi_set_dai_fmt,
.set_sysclk = fsl_ssi_set_dai_sysclk,
+ .set_tdm_slot = fsl_ssi_set_dai_tdm_slot,
.shutdown = fsl_ssi_shutdown,
.trigger = fsl_ssi_trigger,
};