Problem - Wav audio file plays a little bit faster than it must

Status
Not open for further replies.

v_zhukov

Member
While building my project using teensy 3.6 and audio shield I have a problem. The wav audio file plays a little bit faster that it must. I start playing the same file from my PC and from Teensy using AudioPlaySdWav object. The playing process starts at the same time perfectly synchronized. But after 3-4 minutes of playing I hear a noticable difference in time between my pc's audio and teensy's one. Teensy plays the track a little bit faster. And at 4-5th minute I hear this difference clearly. No clicks/pops are heard during playing. Only audio shield accesses SD card during playing. SD card is 32Gb Sandisk Ultra.

How can I solve this problem? I really need accurate timing as my wav track must be perfectly synchronized with other actions Teensy does in background.
 
Is it actually the wave file playback, or simply that the Teensy CPU is not precisely calibrated? The crystals on the teensy are good but if you are after really precise timing you would need to look into measuring temperature and adjusting the clock triming register to ensure calibration at your ambient temperature

Suggested check would be to Serial print a count every 10 seconds per Teensy time and compare them to your desktop, which may not be running dead on time either come to that. May also be worth testing wave files with known (long) lengths against some known precise time source.

It may also be meaningless since if the wave playback is a repeatable number of clock cycles your other background processes will stay in sync with it anyway. The audio library buffers to handle SD card variations during play but the time from ordering start of playback to actually getting audio off the card may have small random variations going on if you are looping the track.
 
Thanks for reply!

Teensy's CPU clock timing is ok. It's the first thing I've checked. Checked with PC's clock it's really accurate.
 
Last edited:
IIRC, that is normal and expected behavior... There is no way inside the Teensy to get the 44100Hz audio sample rate by integer division from the 48MHz bus clock. The closest possible is 48MHz / 1088 which gives 44117.65Hz which leads to a pitch error of only +0.69cts (you'll hardly hear it). But it will naturally advance by 17.65 samples per second or ~1059 samples per minute, which increases the (negative) delay by roughly 24ms per minute. After about 42 minutes, the Teensy's audio will be in advance by 1s. That's nothing to worry about and still an excellent result for an embedded system.
 
Is there a way to solve it?

The pitch error is not so important. But timing error really matters. My teensy plays a wav file along with the metronome clicks (which are accurately generated by teensy).
Sometimes I have a 10-15 minutes long wav tracks. With these teensy playing errors I'll have a 240-260 ms negative delay at the end of a track and it will be totally unsynchronized with the metronome.
 
You can solve it by modifying the audio library in many places to use a sampling rate of 48000Hz, then recording your wavs again at 48kHz, too.

Another (much simpler) way is generating your metronome clicks with exactly the same error. Activating the PDB0 interrupt, so that it is triggered each time when the DAC's DMA is triggered, and do some counter arithmetics in the ISR to trigger the clics always after n samples.
 
Just thinking out loud here, haven’t tried it, but….maybe create new Metronome class for the audio library per:
https://www.pjrc.com/teensy/td_libs_AudioNewObjects.html

The update() function for this object will be called with a frequency of exactly (Teensy Audio Sample Rate) / 128 ~= 344.7 Hz. That’s the same for all Audio library objects and it will be precisely synchronous with them. So then, have your new object keep track of update() invocations and divide the rate down appropriately to generate your metronome clicks.
 
Status
Not open for further replies.
Back
Top