micropython frequency measuring

All ESP8266 boards running MicroPython.
Official boards are the Adafruit Huzzah and Feather boards.
Target audience: MicroPython users with an ESP8266 board.
452
Posts: 4
Joined: Fri Jun 17, 2016 9:21 pm

micropython frequency measuring

Post by 452 » Fri Jun 17, 2016 9:26 pm

please provide examples who have someone, how to measuring a frequency in micropython on ESP8266 board
how many Hz or MHz on pin5 for example

User avatar
deshipu
Posts: 1388
Joined: Thu May 28, 2015 5:54 pm

Re: micropython frequency measuring

Post by deshipu » Sat Jun 18, 2016 10:41 am

The ESP8266 port doesn't support pin interrupts (yet?), so it's hard to do this reliably.

You might be able to cobble something together using http://micropython.org/resources/docs/e ... e_pulse_us perhaps...

Normally the way you do it, you set up a pin interrupt that counts the number of changes of the signal, let it count for a set amount of time, and then divide the count you got by the time -- that's your frequency. Not sure how to do that without interrupts.

markxr
Posts: 62
Joined: Wed Jun 01, 2016 3:41 pm

Re: micropython frequency measuring

Post by markxr » Sat Jun 18, 2016 10:53 am

If you're happy to do busy-waiting, you can just sit in a loop and count pulses.

This is not ideal though, as you might miss pulses if they're too fast or the CPU needs to do something else. As you're presumably aware, the esp8266 has other tasks to do on its cpu including handling wifi interrupts.

If you disable the radio while counting pulses, presumably that's ok.

I think there might be a way to disable interrupts in some versions of Micropython - you could do that, but not for too long as the device won't be able to handle radio requests (e.g. respond to probe requests, send acknowledgements; spend too long and wifi connection will be lost).

So if you're counting very fast pulses for a short time, it's probably ok provided they are not *too* fast.

Also, don't allocate memory inside your pulse-counting loop otherwise the garbage collector will have to run.

User avatar
deshipu
Posts: 1388
Joined: Thu May 28, 2015 5:54 pm

Re: micropython frequency measuring

Post by deshipu » Sat Jun 18, 2016 11:38 am

I just realized that pin interrupts are actually implemented, just not documented!

Something like this should work, more or less:

Code: Select all

import time
from machine import Pin, Timer

pin = Pin(2)
count = 0
frequency = 0

def total(t):
    frequency = count
    count = 0

pin.irq(trigger=Pin.IRQ_FALLING, handler=lambda x: count+=1)
timer = Timer(-1)
timer.init(period=1000, mode=Timer.PERIODIC, callback=total)

time.sleep(1)

print(frequency)


452
Posts: 4
Joined: Fri Jun 17, 2016 9:21 pm

Re: micropython frequency measuring

Post by 452 » Sat Jun 18, 2016 3:21 pm

I create simple class
store this class in /git/micro.../esp.../scripts/freq.py
>>> import freq
>>> f = freq.Freq()
>>> f.freq_start()
>>> # make interupt on pin D5
>>> MemoryError:
MemoryError:
MemoryError:
MemoryError:
MemoryError:

what is wrong?

Code: Select all

import machine
import time
import os
import sys
from machine import Timer, Pin

class Freq:
	def __init__(self):
		machine.freq()          # get the current frequency of the CPU
		machine.freq(160000000) # set the CPU frequency to 160 MHz
		self.PIN_D5 = 14
		self.pin5 = Pin(self.PIN_D5, machine.Pin.IN, machine.Pin.PULL_UP)
		self.PIN_D6 = 15
		self.pin6 = Pin(self.PIN_D6, machine.Pin.OUT, machine.Pin.PULL_UP)
		self.count = 0
		self.frequency = 0
		print('Freq init Done.')
	def freq_start(self):
		self.pin5.irq(trigger = Pin.IRQ_RISING, handler = lambda x: self.inc)
		self.inc(self)
		timer = Timer(-1)
		timer.init(period=1000, mode=Timer.PERIODIC, callback= lambda t: self.total)
	def inc(self):
		print('inc Frequency: {}; Count: {};'.format(self.frequency, self.count))
		self.count += 1
	def total(self):
		self.frequency = self.count
		self.count = 0
	def info(self):
		print('Frequency: {}; Count: {}'.format(self.frequency, self.count))
	def freq5Hz(self):
		tim = Timer(-1)
		tim.init(period=5000, mode=Timer.PERIODIC, callback=lambda t:self.pin6.value(not self.pin6.value()))

452
Posts: 4
Joined: Fri Jun 17, 2016 9:21 pm

Re: micropython frequency measuring

Post by 452 » Sat Jun 18, 2016 4:23 pm

and how to get a time period between pulses on some input pin? be wonderful to get code example on micropython
I think this is basics things and why it's not documented, or have no code examples...

User avatar
deshipu
Posts: 1388
Joined: Thu May 28, 2015 5:54 pm

Re: micropython frequency measuring

Post by deshipu » Sat Jun 18, 2016 9:47 pm

452 wrote:and how to get a time period between pulses on some input pin? be wonderful to get code example on micropython
You can use the function from the first link I gave you.
452 wrote:I think this is basics things and why it's not documented, or have no code examples...
Because writing documentation takes time, and it's either that or developing Micropython further and making it better. You can help too -- if you see some part that you could write documentation for, don't hesitate.

452
Posts: 4
Joined: Fri Jun 17, 2016 9:21 pm

Re: micropython frequency measuring

Post by 452 » Sun Jun 19, 2016 10:37 am

thanks for response =)

I trying to generate pulses on some pin with led and I connect to this pin another one where I check pulse time

Code: Select all

	def genHz(self, pin, period):
		pin_out = Pin(pin, machine.Pin.OUT, machine.Pin.PULL_UP)
		self.generator_timer.init(period = period, mode = Timer.PERIODIC, callback = lambda t:pin_out.value(not pin_out.value()))


but this code is bloking

Code: Select all

	def getPulse(self, pin = 14, time_out = 1000000):
		pulse = machine.time_pulse_us(machine.Pin(pin), 1, time_out)
		print('Pulse time: {} us, on pin {}'.format(pulse, pin))
how to make the code for getting pulse time without blocking operation?

User avatar
deshipu
Posts: 1388
Joined: Thu May 28, 2015 5:54 pm

Re: micropython frequency measuring

Post by deshipu » Sun Jun 19, 2016 12:20 pm

For that again you would need to use the pin interrupts. Have the interrupt save the exact time when it's called, and use the difference from the time when you sent the signal.

ebike
Posts: 55
Joined: Thu Jul 16, 2015 9:36 pm

Re: micropython frequency measuring

Post by ebike » Sun Jul 17, 2016 10:33 pm

Hi,

I have a similar requirement where I want to periodically measure the freq/width of an input signal. The input signal will vary in frequency between 1 and 10Mhz, and the sampling rate that I do this measurement can be as slow as 10khz ..

I presume I could in assembly do a busy wait on an edge, record the system timer, wait for the next edge, record the timer again, and measure the difference ... does anyone have any assembly examples that would do something like that.

I am wanting to implement a PLL in python ...

Post Reply