From bfb650d199790d620144ca15362652915a3eeadc Mon Sep 17 00:00:00 2001 From: Mikey Sklar Date: Tue, 21 Apr 2026 07:23:39 -0700 Subject: [PATCH 1/3] =?UTF-8?q?Revert=20"docs(sdcardio):=20clarify=20SD-fi?= =?UTF-8?q?rst=20init=20rule=20for=20boards=20with=20floating=20C=E2=80=A6?= =?UTF-8?q?"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- shared-bindings/sdcardio/SDCard.c | 7 ------- 1 file changed, 7 deletions(-) diff --git a/shared-bindings/sdcardio/SDCard.c b/shared-bindings/sdcardio/SDCard.c index 9a04cea57e594..2802499956c36 100644 --- a/shared-bindings/sdcardio/SDCard.c +++ b/shared-bindings/sdcardio/SDCard.c @@ -43,13 +43,6 @@ //| Failure to do so can prevent the SD card from being recognized until it is //| powered off or re-inserted. //| -//| Exception: on boards where another SPI peripheral has a floating CS -//| pin with no hardware pull-up (such as the Feather RP2040 RFM), that -//| peripheral's CS must be driven HIGH before SD card initialization. -//| Failure to do so will corrupt the SPI bus during SD card init. In -//| these cases, initialize and drive the other peripheral's CS high -//| first, then initialize the SD card. -//| //| Example usage: //| //| .. code-block:: python From d06079ed1fa30a55d2509bdd214f2a84ae86d16c Mon Sep 17 00:00:00 2001 From: Mikey Sklar Date: Tue, 21 Apr 2026 07:28:24 -0700 Subject: [PATCH 2/3] docs(sdcardio): describe the real shared-SPI CS invariant The previous ".. important::" note said SD card init must come first on a shared SPI bus. That rule happened to work when every co-resident CS line had a hardware pull-up, but it is not the real invariant: what actually matters is that every CS on the shared bus is in a known HIGH (deselected) state before any SPI transaction. On boards where a CS floats (e.g. the Feather RP2040 RFM, whose RFM_CS has no pull-up), it must be driven HIGH in software; init order is secondary. --- shared-bindings/sdcardio/SDCard.c | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/shared-bindings/sdcardio/SDCard.c b/shared-bindings/sdcardio/SDCard.c index 2802499956c36..aa1fecd85f3fc 100644 --- a/shared-bindings/sdcardio/SDCard.c +++ b/shared-bindings/sdcardio/SDCard.c @@ -38,10 +38,18 @@ //| the microcontroller) //| //| .. important:: -//| If the same SPI bus is shared with other peripherals, it is important that -//| the SD card be initialized before accessing any other peripheral on the bus. -//| Failure to do so can prevent the SD card from being recognized until it is -//| powered off or re-inserted. +//| When the SPI bus is shared with other peripherals, every CS pin on +//| the bus must be in a known HIGH (deselected) state before any SPI +//| transaction occurs. This is normally guaranteed by a hardware +//| pull-up on each CS line, but on boards where a co-resident +//| peripheral's CS floats (for example the Feather RP2040 RFM, whose +//| ``RFM_CS`` has no pull-up), that CS must be driven HIGH in +//| software before the SD card is initialized. If any CS is allowed +//| to float low, the SPI bus can be corrupted during SD card init +//| and the card may not be recognized until it is powered off or +//| re-inserted. The order in which peripherals are constructed is +//| secondary; what matters is that all CS lines are deselected +//| before any SPI transaction. //| //| Example usage: //| From 710b77b975d0fc0ad635d0b90cfe88a3ce12c582 Mon Sep 17 00:00:00 2001 From: Mikey Sklar Date: Tue, 21 Apr 2026 07:48:03 -0700 Subject: [PATCH 3/3] Update shared-bindings/sdcardio/SDCard.c Co-authored-by: Dan Halbert --- shared-bindings/sdcardio/SDCard.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/shared-bindings/sdcardio/SDCard.c b/shared-bindings/sdcardio/SDCard.c index aa1fecd85f3fc..79f0a83b8cf9f 100644 --- a/shared-bindings/sdcardio/SDCard.c +++ b/shared-bindings/sdcardio/SDCard.c @@ -48,7 +48,7 @@ //| to float low, the SPI bus can be corrupted during SD card init //| and the card may not be recognized until it is powered off or //| re-inserted. The order in which peripherals are constructed is -//| secondary; what matters is that all CS lines are deselected +//| secondary; what matters is that all CS lines are HIGH (deselected) //| before any SPI transaction. //| //| Example usage: