timer isr function problem

General discussions and questions abound development of code with MicroPython that is not hardware specific.
Target audience: MicroPython Users.
wwsheldons
Posts: 31
Joined: Wed Dec 02, 2015 1:47 pm

timer isr function problem

g = Pin(Pin('Y10'), Pin.OUT_PP)
def tick4(timer):
global g
g.value(not g.value())

tim4 = Timer(4, freq=100000)
tim4.callback(tick4)

the program is above, but if I use the Oscilloscope to see the freq of Pin('Y10') , the value is 14.59KHz. so why? it is why not 50KHz.

Online
Roberthh
Posts: 1795
Joined: Sat May 09, 2015 4:13 pm
Location: Rhineland, Europe

Re: timer isr function problem

The code itself looks fine, so it#s most likely that the Python code cannot run that fast. Try lower speeds and see, at what frequency it is not working any more as expeced. If you need higher frequency signals, use PWM.

chuckbook
Posts: 110
Joined: Fri Oct 30, 2015 11:55 pm

Re: timer isr function problem

Just out of curiosity and not that it would make any sense.

If I try on my pyboard:

Code: Select all

``````from pyb import Pin, Timer

g = Pin(Pin('Y10'), Pin.OUT_PP)

@micropython.viper
def tick(t):
g(not g())

t4=Timer(4, freq=100000)
t4.callback(tick)
``````
I get 50 kHz on Y10 and REPL is still responding.

wwsheldons
Posts: 31
Joined: Wed Dec 02, 2015 1:47 pm

Re: timer isr function problem

chuckbook wrote:
Wed Feb 28, 2018 8:42 pm
Just out of curiosity and not that it would make any sense.

If I try on my pyboard:

Code: Select all

``````from pyb import Pin, Timer

g = Pin(Pin('Y10'), Pin.OUT_PP)

@micropython.viper
def tick(t):
g(not g())

t4=Timer(4, freq=100000)
t4.callback(tick)
``````
I get 50 kHz on Y10 and REPL is still responding.
no, I get 35.78KHz on Y10 , and REPL is not reponding

wwsheldons
Posts: 31
Joined: Wed Dec 02, 2015 1:47 pm

Re: timer isr function problem

chuckbook wrote:
Wed Feb 28, 2018 8:42 pm
Just out of curiosity and not that it would make any sense.

If I try on my pyboard:

Code: Select all

``````from pyb import Pin, Timer

g = Pin(Pin('Y10'), Pin.OUT_PP)

@micropython.viper
def tick(t):
g(not g())

t4=Timer(4, freq=100000)
t4.callback(tick)
``````
I get 50 kHz on Y10 and REPL is still responding.
my whole question is I want to generate a M code in 50KHz, so my program is :

Code: Select all

``````from pyb import Pin, Timer
N_seq = 1023
loc = 0
seq = [1,-1,1,1,-1,-1,-1,...]
g = Pin(Pin('Y10'), Pin.OUT_PP)

@micropython.viper
def tick(t):
global loc,N,seq,g
g.value(not (not seq[loc]))
loc = (loc+1) % N_seq

t4=Timer(4, freq=100000)
t4.callback(tick)
``````
and then I can get the M sequence on Y10, but I get "ViperTypeError: can't do binary op between 'object' and 'int''" in line "loc = (loc+1) % N_seq"

but 10KHz is OK

pythoncoder
Posts: 3867
Joined: Fri Jul 18, 2014 8:01 am
Location: UK
Contact:

Re: timer isr function problem

The problem here is that Viper likes to know the type of variables. Where variables are passed as function arguments you can use Python type hinting to solve this, but this isn't an option in a timer ISR. One solution is to use the Native decorator, but the code won't be as fast. You could do

Code: Select all

``````def tick(t):
func(loc, N_seq)

@micropython.viper
def func(loc: int, N_seq: int):
g.value(not (not seq[loc]))
loc = (loc + 1) % N_seq
``````
but I don't know if the overhead of the function call might negate the advantage of the viper code emitter.

Other optimisations might be possible. Is N_seq a constant? If so, you could save the time taken by a variable lookup by
declaring it a constant (using micropython.const). Further, if it is always of form 0b1111...11 perhaps this might be faster as there's no implied division operation:

Code: Select all

``````loc += 1
loc &= N_seq``````
Incidentally are you sure the line

Code: Select all

``g.value(not (not seq[loc]))``
does what you want it to do?
Peter Hinch

wwsheldons
Posts: 31
Joined: Wed Dec 02, 2015 1:47 pm

Re: timer isr function problem

Code: Select all

``g.value(not (not seq[loc]))``
its for changing the element in seq to the logic variable, which can be accepted by g.value().

Code: Select all

``````@micropython.viper
def func(loc: int, N_seq: int):
g.value(not (not seq[loc]))
loc = (loc + 1) % N_seq``````
as above program , why not set the variable "seq" and "g" in the input parameters. and it can not implement, I print the "loc", its value is always "1"

Online
Roberthh
Posts: 1795
Joined: Sat May 09, 2015 4:13 pm
Location: Rhineland, Europe

Re: timer isr function problem

in your code snippet, you set
seq = [1,-1,1,1,-1,-1,-1,...]
but both not (not (1)) and not (not (-1)) evaluate to True. That's what @pythoncoder was suspicious about, I guess.
If you write:
seq = [1,0,1,1,0,0,0,...]
then you can directly write that into the pin with:
g(seq[loc])

pin(x) is a shortcut for pin.value(x)

pythoncoder
Posts: 3867
Joined: Fri Jul 18, 2014 8:01 am
Location: UK
Contact:

Quite
Peter Hinch