← index #18080Issue #17047
Related · medium · value 4.293
QUERY · ISSUE

RP2040 PIO: Script fails on some GPIO numbers

openby peterhinchopened 2025-09-15updated 2026-03-25
bug

Port, board and/or hardware

RP Pico (RP2040)

MicroPython version

MicroPython v1.26.1 on 2025-09-11; Raspberry Pi Pico with RP2040

Reproduction

Link GPIO 1-17, attach a scope/LA to GPIO 2, and run the following:

from machine import Pin, PWM
import rp2
import time

inp = Pin(0, Pin.IN)
jmp = Pin(1, Pin.IN)
opp = Pin(2, Pin.OUT, value=1)
pwm = PWM(Pin(17))  # Link GPIO 17 to GPIO 1
pwm.freq(1000)
pwm.duty_u16(0xFFFF // 2)

@rp2.asm_pio(out_init=rp2.PIO.OUT_LOW) 
def sm_test():
    set(x, 0)
    wrap_target()
    wait(0, pins, 1)  # Wait for GPIO 1 to go low
    mov(osr, x)  # Ouput==0 while input==0
    out(pins, 1)
    label("loop")  # Loop until jump pin goes high
    jmp(pin, "pulse") 
    jmp("loop")
    label("pulse")
    mov(osr, invert(x))  # Emit a pulse
    out(pins, 1)
    mov(osr, x)
    out(pins, 1)
    wrap()

sm0 = rp2.StateMachine(0, sm_test, freq=100_000, out_base=opp , in_base=inp, jmp_pin=jmp)
sm0.restart()
sm0.active(1)
while True:
    time.sleep(1)
    print("Running")

Expected behaviour

Expected to output a single pulse on GPIO 2 after every positive going edge of GPIO 17.

Observed behaviour

As written, works as designed.

If the link is changed to link GPIO 17 and 14, and the code changed to read

inp = Pin(13, Pin.IN)
jmp = Pin(14, Pin.IN)

pulses are emitted all the time the input is high. If GPIO 1 is strapped to 3V3, pulses stop. Note GPIO 1 is not referenced in the code.

If GPIO 1 and GPIO 14 are linked it runs as designed. This behaviour continues after a power cycle!

Additional Information

RP2350 behaves similarly except that the sensitivity to GPIO 1 is lacking.

The decorator arg is necessary for the code to work. If this is intended it should be documented as this seems unexpected.

Code of Conduct

Yes, I agree

CANDIDATE · ISSUE

RP2350: PIO scripts fail, despite running on RP2040

closedby peterhinchopened 2025-03-30updated 2025-08-01
bugport-rp2

Port, board and/or hardware

Pico 2

MicroPython version

MicroPython v1.25.0-preview.408.gf315a376b on 2025-03-26; Raspberry Pi Pico2 with RP2350

Reproduction

It has proved hard to produce a minimum repro, what follows is my best shot. The repro is quite fragile - minimal changes cause its behaviour to vary between working and failing.

Link GPIO numbers 1-18 and 2-17 and run the following:

import rp2
from machine import Pin, SPI


@rp2.asm_pio(autopush=True, autopull=True)
def spi_count():
    out(x, 32)
    wait(0, pins, 2)  # CS/ True
    label("loop")
    jmp(pin, "good")
    jmp(x_dec, "loop")
    label("good")
    in_(x, 32)
    label("finish")
    jmp("finish")


class Test:

    def __init__(self, start_pin=0, sm_num=0):
        self._sm1 = rp2.StateMachine(
            sm_num,
            spi_count,
            in_base=start_pin,
            jmp_pin=start_pin + 1,
        )
        self._sm1.active(1)

    def go(self, cs, ck):
        sm = self._sm1
        sm.put(10_000_000)
        cs(0)  # Start
        ck(1)  # Stop
        
        assert sm.rx_fifo(), "Rx fifo is empty."
        print(sm.get())


cs = Pin(17, Pin.OUT, value=1)
ck = Pin(18, Pin.OUT, value=0)

t = Test()
t.go(cs, ck)

Expected behaviour

Result on RP2040 is to print a number around 9999759.

Observed behaviour

RP2350 produces an assertion fail. I assume that the RP2350 is failing to respond to the jump pin.

Additional Information

No, I've provided everything above.

Code of Conduct

Yes, I agree

Keyboard

j / / n
next pair
k / / p
previous pair
1 / / h
show query pane
2 / / l
show candidate pane
c
copy suggested comment
r
toggle reasoning
g i
go to index
?
show this help
esc
close overlays

press ? or esc to close

copied