from machine import Pin
import rp2
import time

PIO_RX_PIN = Pin(26, Pin.IN, Pin.PULL_UP)

@rp2.asm_pio(autopush=True,
             push_thresh=24,
             fifo_join=rp2.PIO.JOIN_RX,
             in_shiftdir=rp2.PIO.SHIFT_LEFT)
def b24in_asm():
    wrap_target()

# loop
    label("loop")
    wait(1, pin, 0)

    set(x, 15)

# high
    label("high")
    nop().delay(1)
    jmp(x_dec, "waiting")

    set(x, 1)
    in_(x, 1)
    jmp("next")

# waiting
    label("waiting")
    jmp(pin, "high")

# low
    set(x, 0)
    in_(x, 1)
    jmp("next")

# next
    label("next")
    wait(0, pin, 0)
    wrap()

sm = rp2.StateMachine(0,
                      b24in_asm,
                      freq=125_000_000,
                      in_base=PIO_RX_PIN,
                      jmp_pin=PIO_RX_PIN)
sm.active(1)

from ssd1306 import SSD1306_I2C
from machine import I2C
from time import sleep

i2c = I2C(1, scl=Pin(7), sda=Pin(6), freq=200000)
oled = SSD1306_I2C(128, 64, i2c)

oled.fill(0)
oled.text("ready", 0, 0)
oled.show()
sleep(2)

while True:
    m = ""
    while sm.rx_fifo() > 0:
        v = sm.get()
        m += chr((v >> 8) & 255) + chr((v >> 16) & 255) + chr(v & 255)

    if len(m) > 0:
        oled.fill(0)
        oled.text(m, 0, 0)
        oled.show()
