# Frequency measurement using PIC

I am trying to write a program that measures the frequency of a signal. So I think a way to do it is to set the timer0 interrupt at every rising edge then record that value and subtract two successive values that would give the period. Can anyone tell me if this would work and help me write a code I am a beginner at PIC programming. I am using PIC16f17889

• I am having trouble enabling the Peripheral and Global Interrupts. Any help with that (with explanation) would be appreciated. Commented Feb 22, 2015 at 1:56
• Please provide more details on your environment. Which toolchain (compiler) are you using? Also, maybe you're also using some extra libraries/frameworks for your MCU? Or you just want to configure your MCU via writing in registers (not using any API provided by compiler/libraries)?
– Sam Protsenko
Commented Feb 22, 2015 at 2:09
• I am writing in C. I am using xc8 compiler. Commented Feb 22, 2015 at 2:11
• Google is your friend. If you put the following words into Google, you will find dozens of examples written both in C as well as assembler. Words are: pic frequency counter code Commented Feb 24, 2015 at 15:43

We're not going to spoon feed you code, because you won't learn anything that way. However, I hope we will be able to help you understand the underlying theories.

There's a number of different ways of measuring frequency. Briefly these are:

• Period Measuring
• Edge Counting
• Gated Timing
• FFT

Period measuring is basically what you are suggesting in your question. Measure the time between one leading (or falling) edge and the next. For this to be accurate you need to have a timer that is capable of running faster than the highest frequency you want to measure. Your system has to be able to react quick enough to time between the edges without missing an edge.

Edge counting is a simpler system to implement and can allow for measuring of higher frequencies than the period measuring, but only gives you an average frequency over a short period. This basically works by counting the number of incoming edges of the waveform over a pre-defined period. The simplest period to use is one second. Every time an edge is seen by the input pin you increment a counter. Every second you return that count and reset it to zero. It could be done by using an interrupt pin, or a timer with the clock source set to be an input pin. The latter is more accurate at higher frequencies if you have the ability on your chip.

Gated timing is probably the most fun, but requires specific facilities on your chip. Some timers are able to run in "gated" mode, whereby they count up at the system clock frequency (or some derivative of it) only when a certain input pin is in a HIGH state. Couple that with a second timer to measure the time between gate activations and you not only have the period of the wave but also the duty cycle.

FFT, or Fast Fourier Transform, is the most mathematically intensive. However it can give you frequency information about more complex waveforms. This is probably way beyond the scope of a PIC16 but worth mentioning anyway. With FFT you record a set of samples (analog) into memory then perform the FFT transformation. The result is a set of "buckets", each one representing the amplitude of a range of frequencies. Not really what you're looking for when you just want to measure the frequency of a square wave, but may be worth knowing it exists for a future project.

So which method should you use? Well, that is very subjective. It all depends on the frequency ranges you are looking to measure, the accuracy you want to achieve, whether you are interested in the duty cycle or not, and what facilities your chip provides. Now you know more about the options you can start looking in to which method is best for you.

• There are low resource fft algorithms that 8bit microcontrollers can handle (certainly 18F, not sure about 16F, but wouldn't be surprised) Commented Feb 24, 2015 at 16:07
• @ScottSeidman It's not so much about processing resources, but more about the lack of memory for storing a large enough sample set to be useful. Commented Feb 24, 2015 at 19:35
• It would be worth mentioning that noise in the signal is going to need to be dealt with otherwise most of these solutions won't work. Commented Sep 4, 2015 at 7:06

Take a look at my frequency machine I made using PIC16F84A.
http://www.dihav.com/diy.php?id=frequencymachine