[alsa-devel] [PATCH 0/5] ASoC: fsl_ssi: Fixing various channel slips and bad samples insertions

Caleb Crome caleb at crome.org
Sat Jan 9 01:47:15 CET 2016


On Thu, Nov 26, 2015 at 6:07 AM, Arnaud Mouiche
<arnaud.mouiche at invoxia.com> wrote:
> This series of patch is an attempt to fix the fsl_ssi driver to use it in TDM mode (DSP A or B) with a large number of channels/slots.
>
> Bugs are detected and fixed on a imx6sl platform with linux 4.3, where 2 SSI interfaces are used. SSI3 configured as a master of the bus, SSI2 as a slave.
>
> Various loopback scenario are tested:
> * scenario 1: SSI3 (master) with TXD to RXD loopback
>
>                  |
>                  |---> TXD  --\
>         SSI3     |<--- RXD  --/
>         (master) |---> SYNC
>                  |---> BCLK
>                  |
>
> * scenario 2: SSI3 connected to SSI2
>                  |
>                  |---> TXD  --------\
>         SSI3     |<--- RXD  -----\  |
>         (master) |---> SYNC --\  |  |
>                  |---> BCLK   |  |  |
>                  |       |    |  |  |
>                  |       |    |  |  |
>                  |<--- BCLK   |  |  |
>         SSI2     |<--- SYNC --/  |  |
>         (slave)  |---> TXD ------/  |
>                  |<--- RXD  --------/
>                  |
>
>
>
> A test software (called atest) was developed and available. [1]
> It basically generate/check specials frames with S16_LE sequence samples
>        NNN0, NNN1, NNN2 ... NNNC     with NNN = frame number, and C the number of channels-1
>
>
>
> Patch 1:
>         Limitation fix. Prerequisite to use the fsl_ssi driver with up to 32 channels / slots
>
> Patch 2:
>         Bug fix. Prerequisite to setup a relative high bitclk for our tests in 8ch / 16bits / 48kHz
>
> Patch 3:
>         Simply save a 'dev' reference inside ssi_private for dev_err() purpose.
>         (ssi_private is only available in lot of places, and
>          ssi_private->pdev is deprecated and NULL indeed)
>
> Patch 4:
>         Fix playback samples being dropped because the TX fifo was not ready at
>         the time the DMA starts filling (only in case where playback is started AFTER the capture)
>
>         Detected in loopback scenario 1, with following script (> 80 % of reproducibility)
>         $ atest -D SSI3 -c 8 -r 48000 capture play
>         dbg: set period size: 960
>         dbg: SSI3: capture_start
>         dbg: SSI3: playback_start
>         err: invalid frame after 1 null frames
>         err:   0000 0000 0013 0014 0015 0016 0017 0020
>         dbg: SIGINT
>         total number of sequence errors: 21119
>
>         here we see that samples 0000 0001 ... 0012 are not present in the output.
>         In addition, this the number of samples dropped is not a multiple of
>         the number of channel, we have a a channel slip.
>
>
> Patch 5:
>         This is the Caleb Crome's case [2], where the SSI starts to generate samples while
>         the TX FIFO is not filled by the DMA yet. Void samples can be inserted before DMA streaming.
>
>         Detected in loopback scenario 2, with following script (reproducibility < 1%)
>         $ atest -D SSI3 -c 8 -r 48000 capture &
>         $ sleep 0.2
>         $ atest -d 1 -D SSI2 -c 8 -r 48000 play
>         dbg: SSI3: capture_start
>         dbg: set period size: 960
>         dbg: SSI2: playback_start
>         dbg: start a 1 seconds duration timer
>         err: invalid frame after 11568 null frames
>         err:   0000 0010 0011 0012 0013 0014 0015 0016
>         err:   0017 0020 0021 0022 0023 0024 0025 0026
>
>
>
> Patch 6:
>         Deals with Capture restart whereas Playback is still running
>         (or the opposite, Playback restart whereas Capture is till running).
>
>         Capture restart whereas Playback case is detected in
>         loopback scenario 1 (reproducibility 100%).
>         A playback session is running in background, and
>         2 consecutive Captures are performed.
>         The first is fine, the second fails.
>
>         We see at the 2nd capture startup that we receive 15 samples
>         still pending in the RX FIFO from the previous capture session.
>         => We are receiving invalid samples + slips the channels
>
>         $ atest -D SSI3 -c 8 -r 48000 play &
>         dbg: SSI3: playback_start
>         $ atest -d 1 -D SSI3 -c 8 -r 48000 capture
>         dbg: SSI3: capture_start
>         dbg: start a 1 seconds duration timer
>         warn: Valid frame after 1 null frames
>         warn:   3a90 3a91 3a92 3a93 3a94 3a95 3a96 3a97
>         total number of sequence errors: 0
>
>         $ atest -I 5 -d 1 -D SSI3 -c 8 -r 48000 capture  # restart the capture
>         dbg: SSI3: capture_start
>         dbg: start a 1 seconds duration timer
>         err: invalid frame after 1 null frames
>         err:   8dd6 8dd7 8de0 8de1 8de2 8de3 8de4 8de5
>         err:   8de6 8de7 8df0 8df1 8df2 8df3 8df4 c0c0
>         err:   c0c1 c0c2 c0c3 c0c4 c0c5 c0c6 c0c7 c0d0
>         err:   c0d1 c0d2 c0d3 c0d4 c0d5 c0d6 c0d7 c0e0
>         err:   c0e1 c0e2 c0e3 c0e4 c0e5 c0e6 c0e7 c0f0
>
>
>         Playback restart whereas Capture case is also detected with
>         loopback scenario 1 (reproducibility 100%), capturing continuously,
>         and playing by periods of time.
>
>         $ atest -a -D SSI3 -c 8 -r 48000 capture play -r 1000,200
>         dbg: SSI3: capture_start
>         dbg: SSI3: playback_start
>         dbg: SSI3: will stop every 1000 ms during 200 ms
>         warn: Valid frame after 4 null frames
>         warn:   0010 0011 0012 0013 0014 0015 0016 0017
>         warn: SSI3: PT_W4_STOP
>         warn: SSI3: PT_W4_RESTART
>         err: invalid frame after 1602 null frames
>         err:   eaa1 eaa2 eaa3 eaa4 eaa5 eaa6 eaa7 eab0
>         err:   eab1 eab2 eab3 eab4 5810 5811 5812 5813
>         dbg: stop on first error
>         total number of sequence errors: 143
>
>
>
>         Both cases are resolved by using the mostly undocumented SOR.RX_CLR and
>         SOR TX_CLR (we can find the documentation in IMX51 reference manual
>         at section 56.3.3.15).
>
>
> Arnaud
>
>
>
> [1] https://github.com/amouiche/atest
> [2] http://mailman.alsa-project.org/pipermail/alsa-devel/2015-October/099221.html
>
>
> Arnaud Mouiche (5):
>   ASoC: fsl_ssi: The IPG/5 limitation concerns the bitclk, not the
>     sysclk.
>   ASoC: fsl_ssi: Save a dev reference for dev_err() purpose.
>   ASoC: fsl_ssi: Fix samples being dropped as Playback startup
>   ASoC: fsl_ssi: Fix channel slipping in Playback at startup
>   ASoC: fsl_ssi: Fix channel slipping on capture (or playback) restart
>     in full duplex.
>
>  sound/soc/fsl/fsl_ssi.c | 69 ++++++++++++++++++++++++++++++++++++++++++-------
>  1 file changed, 60 insertions(+), 9 deletions(-)
>
> --
> 1.9.1
>
Hello Arnaud,
  I have finally gotten to test your patches, and I'm still having
trouble with channel slips.

I applied your v2 patch set, along with your changes for using a dummy codec.

The full changes are here:
https://github.com/ccrome/linux-caleb-dev/tree/v4.4-rc8-armv7-x3

This ignores most of my previous patches, and uses your code to bring
up the SSI (without a codec) on a wandboard.

I am using SSI3, and doing a hardware loopback between TX and RX.

Here's what I run:
./atest -r 16000 -c 8 -p 2048   -D default play

which plays continuously.

and in another shell:
./atest -r 16000 -c 8 -p 2048  -D default -d 10 capture

which captures for 10 seconds.


The first time I run the capture command, it succeeds, no problem.
> dbg: dev: 'default'
> dbg: default: capture_start
> dbg: start a 10 seconds duration timer
> warn: First valid frame
> warn:   3400 3401 3402 3403 3404 3405 3406 3407
> dbg: end of tests
> total number of sequence errors: 0
> global tests exit status: OK

But the second and all subsequent captures, it fails with channel slips:

> dbg: dev: 'default'
> dbg: default: capture_start
> dbg: start a 10 seconds duration timer
> err: invalid frame after 0 null frames
> err:   d2a1 d2a2 d2a3 d2a4 d2a5 d2a6 d2a7 d2c0
> err:   d2c1 d2c2 d2c3 d2c4 d2c5 d2c6 d2c7 78e0
> dbg: end of tests
> total number of sequence errors: 430080
> global tests exit status: OK

I verified with a scope that the data on the data bus is correct, the
problem is with restarting RX, the RX doesn't synchronize to the frame
sync.  BTW, the RX slot is random. 1/8 times or so, the restarted
capture actually works.

My setup is a single core wandboard (i.mx6 solo), with J1.16 jumpered
over to J1.20 (tx->rx)

Thanks for the patches and for the atest program!  It's really handy :-)

So, I have not messed with water marks, dual fifo, etc with your patches yet.

Any other patches that you think might need to be applied to make the
RX restart work?
-Caleb


More information about the Alsa-devel mailing list