Module rppal::gpio

source ·
Expand description

Interface for the GPIO peripheral.

To ensure fast performance, RPPAL controls the GPIO peripheral by directly accessing the registers through either /dev/gpiomem or /dev/mem. GPIO interrupts are configured using the gpiochip character device.

§Pins

GPIO pins are retrieved from a Gpio instance by their BCM GPIO number by calling Gpio::get. The returned unconfigured Pin can be used to read the pin’s mode and logic level. Converting the Pin to an InputPin, OutputPin or IoPin through the various into_ methods available on Pin configures the appropriate mode, and provides access to additional methods relevant to the selected pin mode.

Retrieving a GPIO pin with Gpio::get grants access to the pin through an owned Pin instance. If the pin is already in use, or the GPIO peripheral doesn’t expose a pin with the specified number, Gpio::get returns Err(Error::PinNotAvailable). After a Pin (or a derived InputPin, OutputPin or IoPin) goes out of scope, it can be retrieved again through another Gpio::get call.

By default, pins are reset to their original state when they go out of scope. Use InputPin::set_reset_on_drop(false), OutputPin::set_reset_on_drop(false) or IoPin::set_reset_on_drop(false), respectively, to disable this behavior. Note that drop methods aren’t called when a process is abnormally terminated (for instance when a SIGINT signal isn’t caught).

§Interrupts

InputPin supports both synchronous and asynchronous interrupt handlers.

Synchronous (blocking) interrupt triggers are configured using InputPin::set_interrupt. An interrupt trigger for a single pin can be polled with InputPin::poll_interrupt, which blocks the current thread until a trigger event occurs, or until the timeout period elapses. Gpio::poll_interrupts should be used when multiple pins have been configured for synchronous interrupt triggers, and need to be polled simultaneously.

Asynchronous interrupt triggers are configured using InputPin::set_async_interrupt. The specified callback function will be executed on a separate thread when a trigger event occurs.

§Software-based PWM

OutputPin and IoPin feature a software-based PWM implementation. The PWM signal is emulated by toggling the pin’s output state on a separate thread, combined with sleep and busy-waiting.

Software-based PWM is inherently inaccurate on a multi-threaded OS due to scheduling/preemption. If an accurate or faster PWM signal is required, use the hardware Pwm peripheral instead.

PWM threads may occasionally sleep longer than needed. If the active or inactive part of the signal is shorter than 250 µs, only busy-waiting is used, which will increase CPU usage. Due to function call overhead, typical jitter is expected to be up to 10 µs on debug builds, and up to 2 µs on release builds.

§Examples

Basic example:

use std::thread;
use std::time::Duration;

use rppal::gpio::Gpio;

let gpio = Gpio::new()?;
let mut pin = gpio.get(23)?.into_output();

pin.set_high();
thread::sleep(Duration::from_secs(1));
pin.set_low();

Additional examples can be found in the examples directory.

§Troubleshooting

§Permission denied

In recent releases of Raspberry Pi OS (December 2017 or later), users that are part of the gpio group (like the default pi user) can access /dev/gpiomem and /dev/gpiochipN (N = 0-2) without needing additional permissions. If you encounter any PermissionDenied errors when constructing a new Gpio instance, either the current user isn’t a member of the gpio group, or your Raspberry Pi OS distribution isn’t up-to-date and doesn’t automatically configure permissions for the above-mentioned files. Updating Raspberry Pi OS to the latest release should fix any permission issues. Alternatively, although not recommended, you can run your application with superuser privileges by using sudo.

If you’re unable to update Raspberry Pi OS and its packages (namely raspberrypi-sys-mods) to the latest available release, or updating hasn’t fixed the issue, you might be able to manually update your udev rules to set the appropriate permissions. More information can be found at raspberrypi/linux#1225 and raspberrypi/linux#2289.

Structs§

  • Interrupt trigger event.
  • Provides access to the Raspberry Pi’s GPIO peripheral.
  • GPIO pin configured as input.
  • GPIO pin that can be (re)configured for any mode or alternate function.
  • GPIO pin configured as output.
  • Unconfigured GPIO pin.

Enums§

  • Built-in pull-up/pull-down resistor states.
  • Errors that can occur when accessing the GPIO peripheral.
  • Pin logic levels.
  • Pin modes.
  • Interrupt trigger conditions.

Type Aliases§

  • Result type returned from methods that can have rppal::gpio::Errors.