SPDIF code

I am starting a new project to build a digital front end for a triamp.
I have already built an analogue system with a signal input filter, digipot attenuator for the 3 frequency channels controlled by an optical encoder followed by 3 stereo amplifiers.
What I am intending to build is a digital signal processor to accept a SPDIF or toslink signal from a cd transporter, a digital frequency filter, attenuator for each of the three frequencies then a dac before the stereo amplifiers.
I have looked at embedded processors and have the teensy 4.1 in mind with the arm processor, this to use for the DSP and dac unit.
I am after help and advice as my programming experience is limited to assembly and pics which I used for the digipots and encoder.
Hopefully I will use C on this system.
I am looking at the SPDIF protocol and see that the clock is built into the biphase data. Does anyone know at code level how to synchronise with the clock.
Any information would be gratefully received as I have to build up very slowly.
 
easiest way is to use an s/pdif receiver chip (e.g. AKM4113, AKM4117, Cirrus CS8416, etc.) which will do the preamble detection, etc. note that AKM's only wafer fab plant had a devastating fire in Oct 2020 which they have not recovered from, so future of AKM spares is extremely sketchy.
 
Thanks for the info, my problem is that it takes me a long time to do these projects by which time the processors are obsolete.
So I would like to try and program the processors from scratch. It makes for a lot more work but hopefully I will learn how the protocol works.
 
The SPDIF stream carries data AND timing.

Let's assume you use some serial interface with DMA for reading the incoming SPDIF stream into memory and interrupts for processing blocks of samples in your CPU. Decoding SPDIF, DSP - it's all just software. But then you will want to pass the samples to some DAC. For the I2S bus you will need to generate a bit clock which fits the data in your memory buffers. This clock should be as precise as possible, because no ASRC in the DAC (e.g. ESS DACs) can remove all the jitter in the bitclock. That's why hardware SPDIF receivers have PLL hardware circuits which recover the clock signal embedded in the SPDIF stream.
 
The SPDIF stream carries data AND timing.

Let's assume you use some serial interface with DMA for reading the incoming SPDIF stream into memory and interrupts for processing blocks of samples in your CPU. Decoding SPDIF, DSP - it's all just software. But then you will want to pass the samples to some DAC. For the I2S bus you will need to generate a bit clock which fits the data in your memory buffers. This clock should be as precise as possible, because no ASRC in the DAC (e.g. ESS DACs) can remove all the jitter in the bitclock. That's why hardware SPDIF receivers have PLL hardware circuits which recover the clock signal embedded in the SPDIF stream.
Thanks for that, it starts to make sense now.
I do take a long time to pick these things up but I get there in the end.
When I built my triamp it took me ages to program the attenuator chip for the three amps but in the end it worked great, I did it all in assembly and ended up with 15 pages of code.
So at this stage I will be gathering information.
The reason for the SPDIF transmitter is so I have a usable signal to develop the filter for the 3 frequency streams.
 
Although it may be possible to implement SPDIF with teensy 4.1 you would get much better result with either a SPDIF receiver chip or with a MCU that has built-in firmware and HW support for SPDIF.
Is this because the receiver chip has the software already built in.
I have looked over the last few years at various chip suppliers and notice that many have stopped supplying dedicated chips. This was the reason that I wanted to develop my own unit based say on a fast processor that I could program myself.
 
A possible pitfall of using a gp processor (like a pi) is interrupts. The syscall's can happen at any time and this is going to hurt your implementation of a pll. The dedicated processors are setup to do the pll. Even low freq stuff like rs232/465 usually has a hardware frontend to do the timing.
 
I have looked at embedded processors and have the teensy 4.1 in mind with the arm processor, this to use for the DSP and dac unit.
...and program ? in arduino ? good luck. :rolleyes:

the "smallest" CPU imho to do this , is something like STM32H743 : has SPDIF input and 3 x I2S outputs (to make 6 ch out) . (can get on Ali)
To make a program for it, i would use the STM32CubeIDE (as i do ).
https://www.st.com/en/development-tools/stm32cubeide.html
And then maybe 300 hours programming... ;)

or - not so much building fun : just buy something , that can do the job; i looked for it and found:
https://www.minidsp.com/products/car-audio-dsp/c-dsp-6x8
 
...and program ? in arduino ? good luck. :rolleyes:

the "smallest" CPU imho to do this , is something like STM32H743 : has SPDIF input and 3 x I2S outputs (to make 6 ch out) . (can get on Ali)
To make a program for it, i would use the STM32CubeIDE (as i do ).
https://www.st.com/en/development-tools/stm32cubeide.html
And then maybe 300 hours programming... ;)

or - not so much building fun : just buy something , that can do the job; i looked for it and found:
https://www.minidsp.com/products/car-audio-dsp/c-dsp-6x8
I did look at the STM32, interesting. Thanks for the info.
Well, only 300 hours, that would take me over a year!!
Now I have a fair bit of info I will look at the options.
Although my analogue triamp unit is really good I thought I should move forward even though it will be a huge amount of work.
I spent a lot of time last year looking at code and theory for digital filters but its really interesting.
 
A possible pitfall of using a gp processor (like a pi) is interrupts. The syscall's can happen at any time and this is going to hurt your implementation of a pll. The dedicated processors are setup to do the pll. Even low freq stuff like rs232/465 usually has a hardware frontend to do the timing.
Ok thanks, so it needs to be almost a bare bones processor.
With my limited experience of pics, for my 3 channel attenuator I used the interrupts to sense any movement of the optical encoder but this was all under my own control so there were no other interrupt signals possible.
 
oo, yes, i missed. But is same F7 series, just H7 is newer and faster - and only 2 or 3 € more. (if can get any STM32xx, this time )

#oldjack i looked at
https://github.com/PaulStoffregen/Audioand this looks good, maybe you can realize your digital crossover in short time with a Teensy 4.1 this way.
But you have to try it with real parts, to see, it works as you want and how is the sound then....
 
Regarding timing information in SPDIF type signals, the least jittery solution for a DAC is FIFO buffering (at the cost of some time-delay), the next best is ASRC (if referenced to a local low-jitter crystal clock, which also serves as the MCLK source for the dac), the worst performer is PLL recovery of MCLK from the SPDIF stream (since the dac is then forced to use a more jittery MCLK time reference).

A good SPDIF receiver chip such as SRC4392 can do both ASRC, and PLL MCLK recovery. Either way some kind of a PLL is involved. In the case of ASRC there is a PPLL (polyphase locked loop) used to estimate selection of correct resampling filter coefficients on the fly. While neither type of PLL can perfectly correct for SPDIF jitter, the advantages of a local crystal clock weigh in favor of ASRC.

One other thing to perhaps to consider, IME typical audio FFT analysis of jitter effects on audio is of limited utility. It works pretty well for seeing deterministic jitter in a SPDIF stream (using J-Test), but it doesn't make it so easy to visualize potential audible effects of nondeterministic jitter and or of close-in phase noise. Therefore some people assume the latter two factors do not matter. Out of sight out of mind, I guess.
 
Last edited: