IRQ to Stop a Script?

General discussions and questions abound development of code with MicroPython that is not hardware specific.
Target audience: MicroPython Users.
Post Reply
twodoctors
Posts: 19
Joined: Tue Jun 28, 2022 11:24 am

IRQ to Stop a Script?

Post by twodoctors » Sun Jul 03, 2022 11:03 pm

Hi all,

Another question from this newbie! Sorry!

I've nearly finished my turning gallery target programme now. I've managed to utilise a 2004 LCD screen and a rotary encoder to drive a menu system on the main.py script. This would open another py script to run a specific timings for the targets. At the natural end of the script, it will bounce back to the main.py script. All that is working fine.

What I'm trying to add now is a "emergency stop" switch on my timing scripts.

Here is the crucial parts of the scripts (removed the lcd.putstr stuff to reduce clutter):

Code: Select all

# Stop Button
stop = Pin(15, Pin.IN, Pin.PULL_DOWN)

# Normal Cycle
def Run():
    #Cycle (0 to ntimes)
    for x in range (0,1):
    # 5 seconds Edge Delay
        utime.sleep(5)
    # Face
        servoA.duty_u16(4500)
      
    # Face time (seconds)
        utime.sleep(8)
    
    # Edge
        servoA.duty_u16(1350)
 
# Normal End
def End():
    # End in Face after (delay)
    utime.sleep(3)
    servoA.duty_u16(4500)

# Interrupt End
def Interrupt(Pin):
    lcd.clear()
    lcd.move_to(3,1)
    lcd.putstr("Stopped by User")    
    # End in Face after (delay)
    servoA.duty_u16(4500)
    quit()

# Interrupt Function
stop.irq(trigger=Pin.IRQ_RISING, handler=Interrupt)

lcd.clear()
servoA.duty_u16(4500)
# 1st Line
lcd.move_to(0, 0)
lcd.putstr("MT Match 4")
lcd.putstr("Go!")
servoA.duty_u16(1350)
utime.sleep(1)

#Run Script
Run()
End()
The IRQ is working to a degree. It is running the function ok, but what I want it to do is to end this script so it will stop completely and go back to main.py. For normal Python, there is the quit() function, sys.exit() and exit(). None of them works in MicroPython as far as I can work out.

Is there a better way of doing this?

Thanks!

User avatar
jimmo
Posts: 2754
Joined: Tue Aug 08, 2017 1:57 am
Location: Sydney, Australia
Contact:

Re: IRQ to Stop a Script?

Post by jimmo » Mon Jul 04, 2022 1:27 am

twodoctors wrote:
Sun Jul 03, 2022 11:03 pm
For normal Python, there is the quit() function, sys.exit() and exit(). None of them works in MicroPython as far as I can work out.
The closest equivalent we have is just to trigger a reset. Either soft (which clears all state starts the VM from the beginning and runs your main.py from scratch) or hard (which triggers a CPU reset). Sounds like soft reset is what you want.

Code: Select all

machine.soft_reset()
FYI if you wanted to make this work with sys.exit instead...
when you call sys.exit, it raises SystemExit. So you can catch this in your main loop and then restart the program.

twodoctors
Posts: 19
Joined: Tue Jun 28, 2022 11:24 am

Re: IRQ to Stop a Script?

Post by twodoctors » Mon Jul 04, 2022 8:57 am

Thanks Jimmo.

I am currently using machine.rest as you suggested. I tried machine.soft_reset and it didn't stop the script for some reason.

Code: Select all

# # Interrupt End
def Interrupt(Pin):
    lcd.clear()
    lcd.move_to(3,1)
    lcd.putstr("Stopped by User")    
    # End in Face after (delay)
    utime.sleep(2)
    machine.reset()

And that works out fine for the program for me.

Someone else suggested using global variable and False the while True statement to break the loop, but not able to work out how to do it yet. Have been trying that for the last hour or so!

(when you are a newbie, you just have to do it the convoluted way! :lol: )

User avatar
jimmo
Posts: 2754
Joined: Tue Aug 08, 2017 1:57 am
Location: Sydney, Australia
Contact:

Re: IRQ to Stop a Script?

Post by jimmo » Mon Jul 04, 2022 12:09 pm

twodoctors wrote:
Mon Jul 04, 2022 8:57 am
Someone else suggested using global variable and False the while True statement to break the loop, but not able to work out how to do it yet. Have been trying that for the last hour or so!

Code: Select all

stop = False

def interrupt_handler():
  global stop
  stop = True
  
def main():
  global stop
  while True:
    stop = False
    while not stop:
      # do stuff

Post Reply