Skip to content

Commit e051ab6

Browse files
kv2019igregkh
authored andcommitted
ASoC: SOF: ipc4-pcm: fix start offset calculation for chain DMA
commit bace10b upstream. Assumption that chain DMA module starts the link DMA when 1ms of data is available from host is not correct. Instead the firmware chain DMA module fills the link DMA with initial buffer of zeroes and the host and link DMAs are started at the same time. This results in a small error in delay calculation. This can become a more severe problem if host DMA has delays that exceed 1ms. This results in negative delay to be calculated and bogus values reported to applications. This can confuse some applications like alsa_conformance_test. Fix the issue by correctly calculating the firmware chain DMA preamble size and initializing the start offset to this value. Cc: [email protected] Fixes: a1d203d ("ASoC: SOF: ipc4-pcm: Enable delay reporting for ChainDMA streams") Signed-off-by: Kai Vehmanen <[email protected]> Reviewed-by: Péter Ujfalusi <[email protected]> Reviewed-by: Bard Liao <[email protected]> Signed-off-by: Peter Ujfalusi <[email protected]> Link: https://patch.msgid.link/[email protected] Signed-off-by: Mark Brown <[email protected]> Signed-off-by: Greg Kroah-Hartman <[email protected]>
1 parent 996b879 commit e051ab6

File tree

3 files changed

+12
-5
lines changed

3 files changed

+12
-5
lines changed

sound/soc/sof/ipc4-pcm.c

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -992,18 +992,24 @@ static int sof_ipc4_get_stream_start_offset(struct snd_sof_dev *sdev,
992992
return -EINVAL;
993993
} else if (host_copier->data.gtw_cfg.node_id == SOF_IPC4_CHAIN_DMA_NODE_ID) {
994994
/*
995-
* While the firmware does not supports time_info reporting for
995+
* While the firmware does not support time_info reporting for
996996
* streams using ChainDMA, it is granted that ChainDMA can only
997997
* be used on Host+Link pairs where the link position is
998998
* accessible from the host side.
999999
*
10001000
* Enable delay calculation in case of ChainDMA via host
10011001
* accessible registers.
10021002
*
1003-
* The ChainDMA uses 2x 1ms ping-pong buffer, dai side starts
1004-
* when 1ms data is available
1003+
* The ChainDMA prefills the link DMA with a preamble
1004+
* of zero samples. Set the stream start offset based
1005+
* on size of the preamble (driver provided fifo size
1006+
* multiplied by 2.5). We add 1ms of margin as the FW
1007+
* will align the buffer size to DMA hardware
1008+
* alignment that is not known to host.
10051009
*/
1006-
time_info->stream_start_offset = substream->runtime->rate / MSEC_PER_SEC;
1010+
int pre_ms = SOF_IPC4_CHAIN_DMA_BUF_SIZE_MS * 5 / 2 + 1;
1011+
1012+
time_info->stream_start_offset = pre_ms * substream->runtime->rate / MSEC_PER_SEC;
10071013
goto out;
10081014
}
10091015

sound/soc/sof/ipc4-topology.c

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,6 @@ MODULE_PARM_DESC(ipc4_ignore_cpc,
3232

3333
#define SOF_IPC4_GAIN_PARAM_ID 0
3434
#define SOF_IPC4_TPLG_ABI_SIZE 6
35-
#define SOF_IPC4_CHAIN_DMA_BUF_SIZE_MS 2
3635

3736
static DEFINE_IDA(alh_group_ida);
3837
static DEFINE_IDA(pipeline_ida);

sound/soc/sof/ipc4-topology.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -250,6 +250,8 @@ struct sof_ipc4_dma_stream_ch_map {
250250
#define SOF_IPC4_DMA_METHOD_HDA 1
251251
#define SOF_IPC4_DMA_METHOD_GPDMA 2 /* defined for consistency but not used */
252252

253+
#define SOF_IPC4_CHAIN_DMA_BUF_SIZE_MS 2
254+
253255
/**
254256
* struct sof_ipc4_dma_config: DMA configuration
255257
* @dma_method: HDAudio or GPDMA

0 commit comments

Comments
 (0)