summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLars-Peter Clausen <lars@metafoo.de>2013-04-15 19:19:55 +0200
committerMark Brown <broonie@opensource.wolfsonmicro.com>2013-04-17 14:25:56 +0100
commit610f780050090db1af024bd060f819478a656cd0 (patch)
treeb45de808e58ddf8c879aa1aca49d6dc1629475a3
parent11a8576a0a3f153784fc4fca28e6fcee83531135 (diff)
downloadlinux-610f780050090db1af024bd060f819478a656cd0.tar.bz2
ASoC: dmaengine-pcm: Add support for platforms which can't report residue
Unfortunately there are still quite a few platforms with a dmaengine driver which do not support reporting the number of bytes left to transfer. If we want to support these platforms in the generic dmaengine PCM driver we have. Signed-off-by: Lars-Peter Clausen <lars@metafoo.de> Tested-by: Stephen Warren <swarren@nvidia.com> Tested-by: Shawn Guo <shawn.guo@linaro.org> Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com>
-rw-r--r--include/sound/dmaengine_pcm.h5
-rw-r--r--sound/soc/soc-generic-dmaengine-pcm.c23
2 files changed, 27 insertions, 1 deletions
diff --git a/include/sound/dmaengine_pcm.h b/include/sound/dmaengine_pcm.h
index 1a7897ab3572..e7052862d6b2 100644
--- a/include/sound/dmaengine_pcm.h
+++ b/include/sound/dmaengine_pcm.h
@@ -86,6 +86,11 @@ void snd_dmaengine_pcm_set_config_from_dai_data(
* makes sense if SND_DMAENGINE_PCM_FLAG_COMPAT is set as well.
*/
#define SND_DMAENGINE_PCM_FLAG_NO_DT BIT(1)
+/*
+ * The platforms dmaengine driver does not support reporting the ammount of
+ * bytes that are still left to transfer.
+ */
+#define SND_DMAENGINE_PCM_FLAG_NO_RESIDUE BIT(2)
/**
* struct snd_dmaengine_pcm_config - Configuration data for dmaengine based PCM
diff --git a/sound/soc/soc-generic-dmaengine-pcm.c b/sound/soc/soc-generic-dmaengine-pcm.c
index d6e638056389..ae0c37e66ae0 100644
--- a/sound/soc/soc-generic-dmaengine-pcm.c
+++ b/sound/soc/soc-generic-dmaengine-pcm.c
@@ -193,6 +193,23 @@ static const struct snd_soc_platform_driver dmaengine_pcm_platform = {
.probe_order = SND_SOC_COMP_ORDER_LATE,
};
+static const struct snd_pcm_ops dmaengine_no_residue_pcm_ops = {
+ .open = dmaengine_pcm_open,
+ .close = snd_dmaengine_pcm_close,
+ .ioctl = snd_pcm_lib_ioctl,
+ .hw_params = dmaengine_pcm_hw_params,
+ .hw_free = snd_pcm_lib_free_pages,
+ .trigger = snd_dmaengine_pcm_trigger,
+ .pointer = snd_dmaengine_pcm_pointer_no_residue,
+};
+
+static const struct snd_soc_platform_driver dmaengine_no_residue_pcm_platform = {
+ .ops = &dmaengine_no_residue_pcm_ops,
+ .pcm_new = dmaengine_pcm_new,
+ .pcm_free = dmaengine_pcm_free,
+ .probe_order = SND_SOC_COMP_ORDER_LATE,
+};
+
static const char * const dmaengine_pcm_dma_channel_names[] = {
[SNDRV_PCM_STREAM_PLAYBACK] = "tx",
[SNDRV_PCM_STREAM_CAPTURE] = "rx",
@@ -226,7 +243,11 @@ int snd_dmaengine_pcm_register(struct device *dev,
}
}
- return snd_soc_add_platform(dev, &pcm->platform,
+ if (flags & SND_DMAENGINE_PCM_FLAG_NO_RESIDUE)
+ return snd_soc_add_platform(dev, &pcm->platform,
+ &dmaengine_no_residue_pcm_platform);
+ else
+ return snd_soc_add_platform(dev, &pcm->platform,
&dmaengine_pcm_platform);
}
EXPORT_SYMBOL_GPL(snd_dmaengine_pcm_register);