Frequency Counters, Opinions?

I've been looking for a good frequency counter and would like to solicit the opinions of those who have experience with these devices.
First, are the built-in "frequency counters" in today's modern oscilloscopes as good as a stand alone unit for low frequency measurement?
Second, what is you're opinion on something like this: http://www.ebay.com/itm/170874206465
Most of what I'll be measuring is < 100MHz clock signals all the way down to 1 PPS signals for time keeping.
First, are the built-in "frequency counters" in today's modern oscilloscopes as good as a stand alone unit for low frequency measurement?
Second, what is you're opinion on something like this: http://www.ebay.com/itm/170874206465
Most of what I'll be measuring is < 100MHz clock signals all the way down to 1 PPS signals for time keeping.
Comments
http://www.wsplc.com/acatalog/SUPER-HUNTER_Watson_Frequency_Counter.html
If you only ever want to measure frequency of logic signals I wouldn't necessarily bother with a special unit, a Prop can be pressed into service (actually having said that I'm surprised there is only one match for "frequency counter" in the Prop Obex...)
Simple counters are easy and cheap to make, it's not rocket science.
Quality is all in the reference.
Most counters allow the use of external references, usually 10MHz.
Really good ones use rubidium references
BTW, make sure the counter can do the inverse, or measure period.
And a big step up is in the front end.
The high end HP counters can also measure the analog phase of the last pulse in the string of pulses they can add at least 2 more digits.
Why is this important?
It, lets say, they added those 2 extra analog digits the count update can happen about 100 times faster than a similar resolution on a regulator counter.
Duane J
For that you need a Reciprocal Counter, and anything half decent these days, should use reciprocal Counting.
Check how many digits they do, and the timebase precision, and there is also this, for low frequencies.
http://www.daqarta.com/dw_freq.htm
I gave the Developer a nudge a while back, and he extended the precision and sampling choices, to allow better than Crystal values. - and I got him to add an update 'Winky' , as I could get mine to sit unchanging over many samples, and that makes you unsure if it is really working
Before, the display LSB was a limiting factor.
Some slope helps, as it uses linear interpolate to resolve the zero crossing.
If you have a 'nothing fancy' counter, you can push up the precision with a TCXO, or higher standard.
Or, you could wait for the Prop II - I think Chip has added some smarter features to the Counters, to better support Reciprocal Counting.
It reads the frequency on P0 and outputs to the PC @ 115200 baud.
It sends the frequency reading with milliHz 0.001Hz resolution.
' Frequency counter (0.5 Hz to 40 MHz) ' Counts frequency on P0, sends ASCII to PC at 115200 Baud ' 1.0 Second gate time (gate time will be longer if frequency is < 2 Hz) ' DEVICE P8X32A, XTAL1, PLL16X XIN 5_000_000 BAUD CON "T115200" ' Baud rate for PC communications Signal PIN 0 INPUT ' Input pin for signal TX PIN 30 HIGH ' Output pin for PC communications cntStart VAR LONG ' "cnt" value at start of measurement cntTime VAR LONG ' elapsed "cnt" clocks sigCnt VAR LONG ' count of how many input pulses have been received temp VAR LONG ' loop counter digit VAR LONG ' current digit digitSum VAR LONG ' Used for leading zero removal ascii HUB STRING (20) ' Holds ascii representation of frequency PROGRAM Start ' Start program at label "Start:" Start: COUNTERA 80, 0, 0, 1, 0 ' Count positive edges on pin 0 DO ' Wait for a signal pulse to syncronize to the system counter WAITPNE Signal, Signal WAITPEQ Signal, Signal phsa = 0 cntStart = cnt - 4 ' Count input pulses until 1.0 seconds have elapsed DO WAITPNE Signal, Signal WAITPEQ Signal, Signal sigCnt = phsa cntTime = cnt - cntStart LOOP UNTIL cntTime > 80_000_000 ' 1.0 Second gate time cntTime = cntTime - 4 ' To account for "sigCnt = phsa" instruction ' Calculate frequency if >= 0.5 Hz IF cntTime <= 160_000_000 THEN ' Since cntTime is in 80MHz units, the frequency is sigCnt / (cntTime / 80_000_000) = Hertz ' Rearranged this can be written as (sigCnt * 80_000_000) / cntTime = Hertz ' ' We want the result in milliHertz (1/1000 of a hertz) so we need to use: ' (sigCnt * 80_000_000_000) / cntTime = milliHertz ' ' Okay, now we have a problem, 80_000_000_000 cannot even be represented in 32 bits. Hmmm ' What if we calculate the answer one digit at a time... ' ' The leftmost digit is 10 MegaHertz and that digit can be calculated as: ' (sigCnt * 8) / cntTime = x0 MegaHertz. This we can do easily. ' ' Now the "trick" is how do we get the next digit ? ' We take the remainder from the division, multiply it by 10 and divide again. ' by repeating this process of taking the remainder and multipling by 10 we ' can get as many digits as we need until we run out of precision. ' digitSum = 0 ' Sum of all digits so far. Used to create replace leading zeros with spaces ascii = "" sigCnt = sigCnt * 8 ' Scale signal count to get MegaHertz digit FOR temp = 0 TO 13 ' 7 digits + decimal point + 3 digits = 11 digits digit = sigCnt / cntTime ' Calculate this digit of result sigCnt = __remainder ' Keep remainder for next digit ' Scale signal count for next digit __temp1 = sigCnt * 2 ' sigCnt = sigCnt * 10 using powers of two sigCnt = sigCnt * 8 sigCnt = sigCnt + __temp1 INC digitSum, digit ' Add this digit's value to sum digit = digit + "0" ' Convert digit to an ascii digit ' If this is a leading zero, make it a space IF temp < 9 AND ' Only use leading spaces for digits higher than the units digit digitSum = 0 THEN ' If the sum is zero, then we have only had "0" digits so far digit = " " ' so use a space instead of a "0" for this digit. ENDIF WRBYTE ascii(temp), digit ' Put digit into the result string ' Insert a comma if needed IF temp = 1 OR temp = 5 THEN INC temp IF digitSum = 0 THEN WRBYTE ascii(temp), " " ELSE WRBYTE ascii(temp), "," ENDIF ENDIF ' Insert decimal point at proper place IF temp = 9 THEN ' If we just processed the units digit, INC temp ' move pointer to the next character in the result string WRBYTE ascii(temp), "." ' and make it a decimal point ENDIF NEXT ' Process all digits WRBYTE ascii(14), " ", "H", "z", 13, 0 ELSE ascii = "Too low (< 0.5Hz)" ascii = ascii + 13 ENDIF SEROUT TX, BAUD, ascii ' Send frequency to terminal LOOP ' Repeat forever END
Bean
Nice, I would tweak the comments just a little, to better match what actually happens in the code
; Reciprocal counter captures the time needed for a whole number of Signal Cycles ' Count input pulses until at least 1.0 seconds have elapsed DO WAITPNE Signal, Signal WAITPEQ Signal, Signal sigCnt = phsa cntTime = cnt - cntStart LOOP UNTIL cntTime > 80_000_000 ' Exit after > ~1.0 Second gate time, on next Signal edge, so time is WHOLE cycles cntTime = cntTime - 4 ' To account for "sigCnt = phsa" instruction
I think this code also has a 'precision corner' - at low speeds the actions will phase-lock to the edges, and time values will be edge aligned, but at higher values the time given will not be so edge locked, as the SW pacing loop takes more than a half-period.
I think the error added is not large, and it will be added on a large edge-count, which can better tolerate small shifts.
Yes, once you have your 'gold-standard' you then know where you are.
Another point on the price/precision curve I quite like, is this one
http://www.digikey.com/product-detail/en/ASVTX-09-20.000MHZ-T/535-9702-1-ND/1578302
As a VCTCXO you can trim this to better then the default ±0.5ppm, if you have a GPS 1pps for example.