Go Down

Topic: Goertzel for reliable DTMF Decoding (Read 10287 times) previous topic - next topic


BTW - where in your code you do sampling of the signal at the required sampling frequency?


I'm not 100% sure what you are asking, I believe the sampling code is in the goertzel.cpp and it happens at the analogRead(0);


I think I have figured out what's happening in that library. As I mentioned, the sampling loop just goes as fast as possible. Your code sets the sampling rate to 9000Hz but I've measured that loop on my Duemilanove with a frequency counter and the loop is more like 8300Hz.
Change your sampling frequency to 8300 and give it a try. On my Arduino it shows a definite peak at 440Hz now.

Don't send me technical questions via Private Message.


Are you using the modified code or the original?

Can you post your code for recording the frequency?

Also I don't believe you can just change the sampling rate without changing "N".


A Mitel MT8870 will give you 4 bit binary outputs and a data ready signal. The device contains the filters for the high and kw frequencies and decode @ < 100mV. I included thee data sheet and I've seen them on Ebay for $3 - $4.00. Much easier than devoting such a large piece of the code space for decoding... another note is that there are DTMF generators that use the same crystal... If you choose another time base only you could easily decode them. This was a common method for semi secure radio based remote control. I used it when building my first amateur radio repeater for shut down and phone patch control.

--> WA7EMS <--
"The solution of every problem is another problem." -Johann Wolfgang von Goethe
I do answer technical questions PM'd to me with whatever is in my clipboard


Sep 03, 2012, 01:58 am Last Edit: Sep 03, 2012, 02:16 am by SexualMoose Reason: 1

I do not want a hardware solution. I already have a perfectly working hardware solution and I am now looking to eliminate it all together. Thanks for your help!

I appreciate the help, but I really just want to get a functional Goertzel algorithm coded. Finalized, the code shouldn't take more than 50 lines of code. I just don't understand the math well enough to lay it out. I understand the steps, the flowchart, and a small amount of the math. I just need some one, who understands the math, to copy the equations and the lay them out like shown in the flow chart as seen here http://www.ti.com/lit/an/spra066/spra066.pdf. Even if the arduino can't sample at 9000, I believe I can adjust the sample rate and "N" later.

Also, Pete, I would really like to know how you monitored the frequency at which it took a sample. That would help immensely, as i would need to adjust it after I implemented it into another batch of code I'm currently working on. The other code shouldn't consume much and I only need to sample at >3300Hz.


I tested it with a slightly modified version of the library which I've attached to this post. I've added code to toggle the output of digital pin 4 so that you can test it yourself. When you do the test, you should modify your code so that it does:
Code: [Select]
  while(1)goertzel.sample(sensorPin); //Will take n samples
This will force it to loop in the sample routine all the time, otherwise you won't get an accurate frequency reading. Then whatever frequency you get on your frequency counter, you use double that value as the sampling frequency.
It is best to leave the counter code in there all the time because removing it will speed up the loop a bit which knocks the sampling frequency out of whack again.

Changes to the library:
- added code to initialize and toggle pin 4 so that a frequency counter can be used to determine the sampling rate
- the library was storing the sampled values as bytes - not integers!
- offset the sample by 512 so that the Goertzel algorithm then uses values in the range -512 to 511

Also I don't believe you can just change the sampling rate without changing "N".

Yes you can. The two values are independent. N determines the bandwidth of the detector. Larger N gives smaller bandwidth. For example with a sampling frequency of 9000 and N=45 the bandwidth will be 200Hz (9000/45). Change N to 90 and the bandwidth will be 100Hz.
NOTE that the maximum value of N allowed by the library is 160. If you exceed that value your sketch will just crash in mysterious ways.

Don't send me technical questions via Private Message.


BTW. This, of course, only decodes one tone. To do DTMF it would have to be modified to decode 8 tones and then compare the amplitudes to figure out whether there's a DTMF tone there and if so which one it is.

Don't send me technical questions via Private Message.


Alright thank you, I'll take a whack at it tonight. I'm at work currently so I won't be able to test it until around midnight.


Change your sampling frequency to 8300 and give it a try. On my Arduino it shows a definite peak at 440Hz now.

That is why I asked :).


Don't send me technical questions via Private Message.



Thanks for the fixes, I rolled them back into my repository

Mines still a general frequency detection library though. If you're looking for a DTMF, Petes new library is still going to be your best bet.

Also. Remember, you can bring bugs or feature requests to a github authors attention by clicking 'issues' so it doesn't take me a year to hear about this :)

Go Up

Please enter a valid email to subscribe

Confirm your email address

We need to confirm your email address.
To complete the subscription, please click the link in the email we just sent you.

Thank you for subscribing!

via Egeo 16
Torino, 10131