diff options
author | Peter Ujfalusi <peter.ujfalusi@ti.com> | 2018-08-31 11:24:56 +0300 |
---|---|---|
committer | Mark Brown <broonie@kernel.org> | 2018-08-31 11:31:03 +0100 |
commit | 5fcb457ac2fdc62c5ff6d3962c958b1301bc5ea1 (patch) | |
tree | d72f760d697f49a8496f737e4b0a17769693d589 /sound/soc/davinci/davinci-mcasp.c | |
parent | 834fe4084d31f30e88a6a2cae25709a38054f839 (diff) |
ASoC: davinci-mcasp: Add support for FIFO usage caused delay reporting
McASP have write and read FIFO, each 64 words deep.
From the WFIFOS/RFIFOS registers we can read the amount of data currently
in the FIFO which can be directly reported as delay.
Signed-off-by: Peter Ujfalusi <peter.ujfalusi@ti.com>
Signed-off-by: Mark Brown <broonie@kernel.org>
Diffstat (limited to 'sound/soc/davinci/davinci-mcasp.c')
-rw-r--r-- | sound/soc/davinci/davinci-mcasp.c | 37 |
1 files changed, 37 insertions, 0 deletions
diff --git a/sound/soc/davinci/davinci-mcasp.c b/sound/soc/davinci/davinci-mcasp.c index f70db8412c7c..267aee776b2d 100644 --- a/sound/soc/davinci/davinci-mcasp.c +++ b/sound/soc/davinci/davinci-mcasp.c @@ -1041,6 +1041,42 @@ static int davinci_mcasp_calc_clk_div(struct davinci_mcasp *mcasp, return error_ppm; } +static inline u32 davinci_mcasp_tx_delay(struct davinci_mcasp *mcasp) +{ + if (!mcasp->txnumevt) + return 0; + + return mcasp_get_reg(mcasp, mcasp->fifo_base + MCASP_WFIFOSTS_OFFSET); +} + +static inline u32 davinci_mcasp_rx_delay(struct davinci_mcasp *mcasp) +{ + if (!mcasp->rxnumevt) + return 0; + + return mcasp_get_reg(mcasp, mcasp->fifo_base + MCASP_RFIFOSTS_OFFSET); +} + +static snd_pcm_sframes_t davinci_mcasp_delay( + struct snd_pcm_substream *substream, + struct snd_soc_dai *cpu_dai) +{ + struct davinci_mcasp *mcasp = snd_soc_dai_get_drvdata(cpu_dai); + u32 fifo_use; + + if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) + fifo_use = davinci_mcasp_tx_delay(mcasp); + else + fifo_use = davinci_mcasp_rx_delay(mcasp); + + /* + * Divide the used locations with the channel count to get the + * FIFO usage in samples (don't care about partial samples in the + * buffer). + */ + return fifo_use / substream->runtime->channels; +} + static int davinci_mcasp_hw_params(struct snd_pcm_substream *substream, struct snd_pcm_hw_params *params, struct snd_soc_dai *cpu_dai) @@ -1365,6 +1401,7 @@ static const struct snd_soc_dai_ops davinci_mcasp_dai_ops = { .startup = davinci_mcasp_startup, .shutdown = davinci_mcasp_shutdown, .trigger = davinci_mcasp_trigger, + .delay = davinci_mcasp_delay, .hw_params = davinci_mcasp_hw_params, .set_fmt = davinci_mcasp_set_dai_fmt, .set_clkdiv = davinci_mcasp_set_clkdiv, |