General Purpose Input/Output (GPIO) pins are the foundation of working with any peripherals.

In Toit, the GPIO Pin class is exposed by the gpio module.

GPIO pins are managed across the device. That means that only one instance of a given GPIO pin can exist at any given point in time. This ensures that two applications can't configure or use a specific GPIO pin at the same time. The pin can be released again by calling close after usage:

import gpio

  pin := gpio.Pin 21  // Acquired system-wide.
  // ...
  pin.close           // Released, can be used by other applications now.

When an application terminates, the pin will automatically be closed and released.

Output mode

If a GPIO pin is configured for output mode, Pin.set can be used to either drive the pin voltage high (1) or low (0).

Set valueEffect
0Low voltage
1High voltage

To configure a GPIO pin in output mode, either do it initially:

  output_pin := gpio.Pin 21 --output // Initialized for output mode.

or later (independent of previous mode):

  pin.config --output         // Reconfigure for output mode.


GPIO pins also supports output mode as open-drain. To configure the GPIO Pin as open-drain output do the following:

  pin.config --output --open_drain

In open-drain output mode, when setting the pin high, the pin will go into open-drain mode. That means the pin is not being pulled in any direction (floating).

Set valueEffect
0Low voltage
1Open drain

This can be useful when an external pull-up is connected to the pin.

Input mode

The GPIO input mode can be used to read the state of a pin. This can be done by calling Pin.get, returning either 0 or 1 depending on the voltage measured at the pin.

To configure a GPIO pin in input mode, either do it initially:

  input_pin := gpio.Pin 21 --input // Initialized for input mode.

or later (independent of previous mode):

  pin.config --input         // Reconfigure for input mode.

Waiting for state change

While Pin.get can be used to get the current Pin state, sometimes it's useful to block and wait until the pin changes state. That can be done using the Pin.wait_for method.

import gpio

  pin := gpio.Pin 21 --input
  pin.wait_for 1  // Wait for pin to be high.

Pull-up and pull-down resistors

Some chips supports internal pull-up and/or pull-down resistors. While the size of the resistor depends on the chip used, it can be enabled like this:

  pulled_up_pin := gpio.Pin 21 --input --pull_up

If a Pin is configured as input with pull-up/pull-down, it automatically disables the pull-up/pull-down if it is reconfigured to output mode - and enables it again when reconfigured back to input.