Time2 interrupt code: normal for example ,run with bug when add the loop and tim.deinit()

# Timer Control Example
#
# This example shows how to use a timer for callbacks.

import time , micropython
from pyb import Pin, Timer, LED

blue_led  = LED(3)

# we will receive the timer object when being called
# Note: functions that allocate memory are Not allowed in callbacks
def tick(timer):            
    blue_led.toggle()
    print('-T2 out-')

tim = Timer(2, freq=1)
tim.prescaler(10) #10 seconds

tim.callback(tick)
Timeout_counter=0
while (True):
    time.sleep_ms(1000)
    Timeout_counter+=1
    print('Timeout_counter=%d' %Timeout_counter)      

the result is following:----------
Timeout_counter=1
-T2 out-
Timeout_counter=2
Timeout_counter=3
Timeout_counter=4
Timeout_counter=5
Timeout_counter=6
Timeout_counter=7
Timeout_counter=8
Timeout_counter=9
Timeout_counter=10
Timeout_counter=11
Timeout_counter=12
-T2 out-
Timeout_counter=13
Timeout_counter=14
Timeout_counter=15
Timeout_counter=16
Timeout_counter=17
Timeout_counter=18
Timeout_counter=19
Timeout_counter=20
Timeout_counter=21
Timeout_counter=22
Timeout_counter=23
-T2 out-
Timeout_counter=24
Timeout_counter=25
Timeout_counter=26
/----------------------------------------/
code print T2 out every 10 second . it is ok.

my code is following:

# Timer Control Example
#
# This example shows how to use a timer for callbacks.

import time , micropython
from pyb import Pin, Timer, LED

blue_led  = LED(3)

# we will receive the timer object when being called
# Note: functions that allocate memory are Not allowed in callbacks
def tick(timer):
    global  tim           
    blue_led.off()
    print('timeout-off')
    tim.deinit()#<---------------
    
tim = Timer(2, freq=1)      # create a timer object using timer 2 - trigger at 1Hz
tim.prescaler(10)
tim.callback(tick)          # set the callback to our tick function

Timeout_counter=0
while (True):
    time.sleep_ms(1000)
    Timeout_counter+=1
    print('Timeout_counter=%d' %Timeout_counter)
    if Timeout_counter==3:
        print('3s-on')
        blue_led.on()
        tim = Timer(2,freq=1)#<---------------
        tim.prescaler(10)#<---------------
        
        tim.callback(tick)##<---------------
  
    if Timeout_counter==15:
        Timeout_counter=0
        print('15s')      

now the result:------------
Timeout_counter=1
timeout-off
Timeout_counter=2
Timeout_counter=3
3s-on
Timeout_counter=4
timeout-off
Timeout_counter=5
Timeout_counter=6
Timeout_counter=7
Timeout_counter=8
Timeout_counter=9
Timeout_counter=10
Timeout_counter=11
Timeout_counter=12
Timeout_counter=13
Timeout_counter=14
Timeout_counter=15
15s
Timeout_counter=1
Timeout_counter=2
Timeout_counter=3
3s-on
Timeout_counter=4
timeout-off
Timeout_counter=5
Timeout_counter=6
Timeout_counter=7
Timeout_counter=8
Timeout_counter=9
‘’’
the timer2 print “timeout-off” after 1 second ,not 10 second.
what is wrong with my code?

Hi, you are deiniting the timer in the callback and dynamically reiniting the timer not necessarily with a deinit. I can’t say what will happen when doing this. You should set a flag (after checking if it was not set) in the callback and then deinit the timer in the main loop if the flag was set (and then clear the flag). Also, only reinit the timer if it was deinited.

thank your for your reply so quickly.
i want to set the t2 interrupt for delay,and clolse the t2( i can’t find the code how to turn off timer)
the main loop init timer is just enable timer.
i just want to run the timer2 for only once by my code in main.
thanks again.

Remember, the overhead of the timer callback is very low. So, you can just leave it on and use global variables to control state. If you don’t feel comfortable turning the timer off then leave it on.

thank you .
how to turn off the timer, my ide shows that timer interrput is still running:-------------


:sob:

Hi, deinit() should work. Make sure it gets called.

1 Like
import time , micropython
from pyb import Pin, Timer, LED

blue_led  = LED(3)

# we will receive the timer object when being called
# Note: functions that allocate memory are Not allowed in callbacks
def tick(timer):
    global flag_time2

    #blue_led.toggle()
    blue_led.off()
    print('timeout-off')
    flag_time2=1

    #Timer.callback(None)
'''
tim = Timer(2, freq=1)      # create a timer object using timer 2 - trigger at 1Hz
tim.prescaler(10)
tim.callback(tick)          # set the callback to our tick function
'''
flag_time2=0
Timeout_counter=0
while (True):
    time.sleep_ms(1000)
    Timeout_counter+=1
    if flag_time2==1:
        tim.deinit()
        flag_time2=0
    print('Timeout_counter=%d' %Timeout_counter)
    if (Timeout_counter==3 and flag_time2==0):
        print('3s-on')
        blue_led.on()
     
        tim = Timer(2)
        tim.init(period=5000) #ms< it is done
        #tim.init(prescaler=10, period=20)
        tim.callback(tick)#off
  
    if Timeout_counter==10:
        Timeout_counter=0
        print('10s')

thanks kwagyeman! :pray:

Hi, just something to make you a better programmer:

flag = False

def callback()
    global flag
    if not flag:
        <do something>
        flag = True

while(True):
    if flag:
        <do something>
        flag = False

Notice how I check the flag state is the opposite of what I’m about to change it to before changing it. This avoids race conditions which can cause bugs in your code. Otherwise the interrupt callback could be modifying the flag at the same time as the main loop is. By adding the if statements they will never overlap.

1 Like