← index #17515Issue #3199
Related · high · value 0.319
QUERY · ISSUE

Add Pin.mode() and Pin.alt() support for all applicable ports

openby sfe-SparkFroopened 2025-06-17updated 2025-06-19
enhancement

Description

Request

Pin.mode() is currently only supported on cc3200 and stm32 ports, according to the current docs. The first part of this request is to implement that method on all other applicable ports (eg. rp2).

The second part of this request is to implement a similar Pin.alt() method for all applicable ports (eg. rp2), that can be used to either get or set the alt value of the Pin object.


Motivation

I'm writing an ST7789 display driver. Yes, there are many out there, but none fit the needs of my application perfectly.

For example, many ST7789 breakout boards include an SD card slot that shares the same SPI bus, but none of the existing ST7789 MicroPython drivers (that I know of) allow both the display and SD card to be used simultaneously. The DC pin of the ST7789 typically shares the MISO pin. The DC pin has to be driven by the host microcontroller, meaning its mode must be set to OUT. However for the SD card, the mode must be set to ALT, and the alt must be set to ALT_SPI (at least, in the case of the rp2 port); having the mode changed to OUT causes the SD card to stop functioning.

My solution is to have my ST7789 driver save the DC pin's mode and alt values before communicating with the ST7789, then restore them after. However, there is no built-in way to get the mode and alt values of the pin directly. Instead, I convert the pin to a string and parse/extract the mode and alt values from there. This works, but the string parsing isn't an efficient solution. Having direct access to the values would be very helpful.

For reference, here's a snippet of my code that saves and restores the mode and alt values:

# There's no way to get the mode and alt of a pin directly, so we
# convert the pin to a string and parse it. Example formats:
# "Pin(GPIO16, mode=OUT)"
# "Pin(GPIO16, mode=ALT, alt=SPI)"
pinStr = str(pin)

# Extract the "mode" parameter from the pin string
if "mode=" in pinStr:
    # Split between "mode=" and the next comma or closing parenthesis
    modeStr = pinStr.split("mode=")[1].split(",")[0].split(")")[0]

    # Look up the mode in Pin class dictionary
    mode = Pin.__dict__[modeStr]
else:
    # No mode specified, just set to None
    mode = None

# Extrct the "alt" parameter from the pin string
if "alt=" in pinStr:
    # Split between "alt=" and the next comma or closing parenthesis
    altStr = pinStr.split("alt=")[1].split(",")[0].split(")")[0]

    # Look up the alt in Pin class dictionary (with "ALT_" prefix)
    alt = Pin.__dict__["ALT_" + altStr]
else:
    # No alt specified, just set to None
    alt = None

#########################
# Communicate with ST7789
#########################

# Restore the pin to its original mode and alt
pin.init(mode=mode, alt=alt)

Code Size

This feature should be always enabled for all ports that support it, to ensure compatibility with drivers that make use of it. I do not expect this to have a significant impact on code size.

Implementation

I hope the MicroPython maintainers or community will implement this feature

Code of Conduct

Yes, I agree

CANDIDATE · ISSUE

Documentation outdated for latest machine.Pin API

closedby cefnopened 2017-07-07updated 2022-03-07
docs

The documentation for Pin says there is a mode method on machine.Pin...

Pin.mode([mode])
Get or set the pin mode. See the constructor documentation for details of the mode argument.

https://docs.micropython.org/en/latest/esp8266/library/machine.Pin.html

However from an interactive session with the latest image I get...

MicroPython v1.9.1-8-g7213e78d on 2017-06-12; ESP module with ESP8266
Type "help()" for more information.
>>> from machine import Pin
>>> pin = Pin(0)
>>> pin.mode()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'Pin' object has no attribute 'mode'

As a workaround I have been aiming to use init() instead, like e.g.

pin.init(mode=Pin.IN)

Keyboard

j / / n
next pair
k / / p
previous pair
1 / / h
show query pane
2 / / l
show candidate pane
c
copy suggested comment
r
toggle reasoning
g i
go to index
?
show this help
esc
close overlays

press ? or esc to close

copied