We use some essential cookies to make our website work.

We use optional cookies, as detailed in our cookie policy, to remember your settings and understand how you use our website.

5 posts • Page 1 of 1
derGerd
Posts: 6
Joined: Fri Jul 25, 2025 6:51 am

PIO wait/jmp requires explicit GPIO function setup – documentation misleading?

Tue Oct 28, 2025 10:17 am

Hi everyone,

I'm working with a custom RP2350 board and encountered an unexpected issue while using PIO to read GPIO input states via wait and jmp. According to the SDK documentation in pio.h, it says:

Code: Select all

/*! rief Setup the function select for a GPIO to use output from the given PIO instance
 * ...
 * Note that this is not necessary for a state machine to be able to read the *input* value from a GPIO, but only for it to set the output value or output enable.
 */
This implies that no explicit pin function setup is needed if you're only reading the pin (e.g., using wait 1 pin X or jmp pin X). However, in practice, I found that the PIO state machine does not respond to pin changes unless I explicitly configure the pin using either:

Code: Select all

gpio_set_function(pin, GPIO_FUNC_SIO);
or

Code: Select all

pio_gpio_init(pio, pin);
Without one of these, the state machine stalls at wait or jmp, even though gpio_get(pin) works fine and reflects the correct pin state.

This behavior was not noticeable on the RP2040, but on the RP2350 (on a custom board), it's reproducible and consistent.

Example PIO program:

Code: Select all

.program in_out
.side_set 1
 wait 1 pin 0 side 0 ; Wait for rising edge
 wait 0 pin 0 side 1 ; Wait for falling edge, set side=1 during transition
Initialization using C SDK:

Code: Select all

% c-sdk{
 static inline void in_out_program_init(PIO pio, uint sm, uint offset, uint pin, uint sideset_pin)
 {
 pio_sm_config c = in_out_program_get_default_config(offset);
 sm_config_set_in_pins(&c, pin); // For wait and in instructions
 sm_config_set_jmp_pin(&c, pin); // For jmp instructions
 pio_gpio_init(pio, pin);
 pio_gpio_init(pio, sideset_pin);
 pio_sm_set_consecutive_pindirs(pio, sm, sideset_pin, 1, true);
 sm_config_set_sideset_pins(&c, sideset_pin);
 pio_sm_init(pio, sm, offset, &c); // Load configuration
 pio_sm_set_enabled(pio, sm, true); // Start the state machine
 }
%}
My questions to the community:
  • Is this a known difference between RP2040 and RP2350?
  • Is there a technical reason why wait/jmp requires explicit pin function setup, even for input-only use?
  • Should the SDK documentation be updated to reflect this?
Thanks in advance for your insights!

Best regards,
Jan-Gerd Meinen

gmx
Posts: 1845
Joined: Thu Aug 29, 2024 8:51 pm

Re: PIO wait/jmp requires explicit GPIO function setup – documentation misleading?

Tue Oct 28, 2025 11:21 am

derGerd wrote: Is this a known difference between RP2040 and RP2350?
Is there a technical reason why wait/jmp requires explicit pin function setup, even for input-only use?
Should the SDK documentation be updated to reflect this?
Yep, there is a hardware difference with the PADs, on RP2350 they have a feature named isolation, and are isolated by default.

From RP2350 datasheet:
9.7. Pad isolation latches
...
NOTE
Non-SDK applications ported from RP2040 must clear the ISO bit before using a GPIO, as this feature was not
present on RP2040. The SDK automatically clears the ISO bit when gpio_set_function() is called.


derGerd
Posts: 6
Joined: Fri Jul 25, 2025 6:51 am

Re: PIO wait/jmp requires explicit GPIO function setup – documentation misleading?

Wed Oct 29, 2025 3:19 pm

Ah, that explains my observation. The comment on pio.h:

Code: Select all

/*! \brief Setup the function select for a GPIO to use output from the given PIO instance
 * \ingroup hardware_pio
 *
 * PIO appears as an alternate function in the GPIO muxing, just like an SPI
 * or UART. This function configures that multiplexing to connect a given PIO
 * instance to a GPIO. Note that this is not necessary for a state machine to
 * be able to read the *input* value from a GPIO, but only for it to set the
 * output value or output enable.
 *
 * \param pio The PIO instance; e.g. \ref pio0 or \ref pio1
 * \param pin the GPIO pin whose function select to set
 */
static inline void pio_gpio_init(PIO pio, uint pin) {
 check_pio_param(pio);
 valid_params_if(HARDWARE_PIO, pin < NUM_BANK0_GPIOS);
 gpio_set_function(pin, PIO_FUNCSEL_NUM(pio, pin));
}
completely misled me.


5 posts • Page 1 of 1

Return to "SDK"

AltStyle によって変換されたページ (->オリジナル) /