User Tools

Site Tools


en:pfw:assemblers_pio-assembler

PIO (dis)assembler v2 for RP2040

The idea:

PIO stand for Programmable Input Output. These are programmable state machines with a small shared program memory. Programs are built with only eight instructions. The behavior of those instructions can be modified with registers.

We define a (standalone) PIO forth style (dis)assembler for the RP2040. It can be used for writing direct executable programs and exportable HEX programs. These HEX programs can be used in conjunction with the mini-PIO control program.

One PIO state machine

Implementation

Note that; this is version-2 of the PIO (dis)assembler.
This version is more flexible and is prepared for more than two PIO's. The sample code assumes a 32-bit machine with 32-bit compile operations. It is also assumed that the code runs in RAM as noForth t on the RP2040 does. All PIO fuctionality can be used, and a PIO-module EXPORT function is provided. The PIO-assembler is (de)activated by the words {PIO and PIO}. Missing words in Generic Forth are:

+TO         ( n "name" -- )     - Add n to the contents of the value "name"
VOCABULARY  ( "name" -- )       - Define a named wordlist

The structure of PIO opcodes

Pink   = Opcode field
Yellow = Delay and/or side set field
Green  = Destination field
Blue   = Data field

set_jpg.jpg

All PIO instructions

✦ PIO opcodes
    in,         out,        push,       pull,       mov,        wait,
    irq,        set,        nop,        pio,        
 
✦  Optional arguments for each opcode
    []         side
 
✦ Conditionals
    x0<>?       x--?        y0<>?       y--?        x=y?        pin?
    osre?
 
✦ Control structures
    if,         else,       then,      begin,      while,      repeat,
    again,      until,
 
✦ Labels
    one         two         three      one>        two>        three>
 
✦ PIO directives
    clean-pio   =pio        sm          sync        restart
    =org        =set-pins   =out-pins   =side-pins  opt
    =in-pin     =jmp-pin    =inputs     =strength   side-pindirs
    wrap-target wrap        =steal      =autopush   =autopull
    =in-dir     =out-dir    clone       =exec       =clock-div
    =freq       export
 
✦ PIO external tools (mini-PIO.f)
    tx-depth    rx-depth    >txf        rxf>        =pio
    sm-on       exec        freq        clock-div   sync
    restart
 
✦ PIO disassembler & state machine data
    psee        psee0       psee1       .fifo       .sm

Usage example

An extra RS232 output driver in only 5 instructions!

decimal
: =BAUD ( b -- )    8 *  =freq ; \ Set baudrate for UART

clean-pio                   \ Empty code space, start at zero
0 0 {pio                    \ Use state machine-0 on PIO-0
    115200 =baud            \ 115k2
    26 1 =side-pins  opt    \ GPIO 26 for optional SIDE
    26 1 =out-pins          \ GPIO 26 for OUT & SET
    26 1 =set-pins
    1 pindirs set,              \ Pin is output!
    wrap-target
        7 []  1 side  pull,     \ Stop bit, get data byte
        7 []  0 side 7 x set,   \ Start bit
        begin,
            1 pins out,         \ Shift 8 bits out
        6 []  x--? until,       \ Until 8 bits are done
    wrap
    0 =exec                 \ Start SM-0 code at address 0
pio}

UART control code

: PEMIT ( ch -- )   begin  0 tx-depth  3 < until  0 >txf ;
: PTYPE ( a u -- )  0 ?do  count pemit  loop  drop ;
: ABC   ( -- )      s" ABC " ptype ;

pio_uart.jpg




Back to PFW page

Contributions

Alternative Implementations

Back to PFW page

en/pfw/assemblers_pio-assembler.txt · Last modified: 2024-09-03 17:15 by willem