Is viper going to be faster than pure Python when toggling GPIOs? (ESP8266)

General discussions and questions abound development of code with MicroPython that is not hardware specific.
Target audience: MicroPython Users.
Post Reply
Posts: 11
Joined: Fri Aug 01, 2014 10:40 pm
Location: Latvia

Is viper going to be faster than pure Python when toggling GPIOs? (ESP8266)

Post by CRImier » Sun Jul 09, 2017 4:12 pm

I'm implementing a shiftOut function in Python to drive a 595 - for my IMTAIDKW project. Here's a Python example of it:

Code: Select all

def shiftOut(byte):
    for i in range(8):
        value = byte & 1<<i #Is bit set or cleared?
Here's a @micropython.viper-ported shiftOut function:

Code: Select all

def shiftOut(data: int):
    GPIO_OUT = ptr32(0x60000300) # GPIO base register
    GPIO_OUT[2] = 0x10 # clear pin 4
    for i in range(8):
        value = data & 1<<i #Is bit set or cleared?
        reg = 2-(value >>i) #Selecting set or clear register - clear reg is 2, set reg is 1
        GPIO_OUT[reg] = 0x8000 #set or clear data bit
        GPIO_OUT[1] = 0x20 # set bit 5
        GPIO_OUT[2] = 0x20 # clear bit 5
Question is - am I getting any speed advantage this way? I'm using it for LED dynamic indication, and I'd like to do something inbetween switching the digits, so I'm interested in shortening the execution time. I'll profile the function when I get to it, but I'm wondering if there's any feedback on this that you could give - it's my first try with viper code and I don't understand the concept enough to know if there are any possible disadvantages.

User avatar
Posts: 5216
Joined: Fri Jul 18, 2014 8:01 am
Location: UK

Re: Is viper going to be faster than pure Python when toggling GPIOs? (ESP8266)

Post by pythoncoder » Mon Jul 10, 2017 5:51 am

If you want to understand the different code emitters see these docs ... sts/664832 and ... sts/665145.

I haven't used the alternative emitters on the ESP8266 but on the Pyboard Viper can help substantially in that kind of bit banging code. Why not measure the difference? Rename the normal version of the function, and call each N times timing the duration.

Code: Select all

from utime import ticks_us, ticks_diff
N = 1000
start = ticks_us()
for _ in range(N):
t_normal = ticks_diff(ticks_us(), start) / N

start = ticks_us()
for _ in range(N):
t_viper = ticks_diff(ticks_us(), start) / N
print('Normal = {}μs Viper = {}μs'.format(t_normal, t_viper))
On my test at standard clock frequency Viper takes 136.5μs. I didn't test the normal version as I don't know where to find the latch and clock functions.

For a way to time a function by simply using a decorator see ...
Peter Hinch

Post Reply