diff --git a/embassy-stm32/src/gpio.rs b/embassy-stm32/src/gpio.rs index 81cb09b24..808a5bc82 100644 --- a/embassy-stm32/src/gpio.rs +++ b/embassy-stm32/src/gpio.rs @@ -681,6 +681,38 @@ pub(crate) trait SealedPin { #[cfg(gpio_v2)] self.block().ospeedr().modify(|w| w.set_ospeedr(pin, speed.into())); } + + /// Get the pull-up configuration. + #[inline] + fn pull(&self) -> Pull { + critical_section::with(|_| { + let r = self.block(); + let n = self._pin() as usize; + #[cfg(gpio_v1)] + { + let crlh = if n < 8 { 0 } else { 1 }; + match r.cr(crlh).read().mode(n % 8) { + vals::Mode::INPUT => match r.cr(crlh).read().cnf_in(n % 8) { + vals::CnfIn::PULL => match r.odr().read().odr(n) { + vals::Odr::LOW => Pull::Down, + vals::Odr::HIGH => Pull::Up, + }, + _ => Pull::None, + }, + _ => Pull::None, + } + } + #[cfg(gpio_v2)] + { + match r.pupdr().read().pupdr(n) { + vals::Pupdr::FLOATING => Pull::None, + vals::Pupdr::PULLDOWN => Pull::Down, + vals::Pupdr::PULLUP => Pull::Up, + vals::Pupdr::_RESERVED_3 => Pull::None, + } + } + }) + } } /// GPIO pin trait. diff --git a/embassy-stm32/src/spi/mod.rs b/embassy-stm32/src/spi/mod.rs index 0875cfe41..5fc8691ac 100644 --- a/embassy-stm32/src/spi/mod.rs +++ b/embassy-stm32/src/spi/mod.rs @@ -50,6 +50,11 @@ pub struct Config { pub bit_order: BitOrder, /// Clock frequency. pub frequency: Hertz, + /// Enable internal pullup on MISO. + /// + /// There are some ICs that require a pull-up on the MISO pin for some applications. + /// If you are unsure, you probably don't need this. + pub miso_pull: Pull, } impl Default for Config { @@ -58,6 +63,7 @@ impl Default for Config { mode: MODE_0, bit_order: BitOrder::MsbFirst, frequency: Hertz(1_000_000), + miso_pull: Pull::None, } } } @@ -273,6 +279,11 @@ impl<'d, M: PeriMode> Spi<'d, M> { BitOrder::MsbFirst }; + let miso_pull = match &self.miso { + None => Pull::None, + Some(pin) => pin.pull(), + }; + #[cfg(any(spi_v1, spi_f1, spi_v2))] let br = cfg.br(); #[cfg(any(spi_v3, spi_v4, spi_v5))] @@ -284,6 +295,7 @@ impl<'d, M: PeriMode> Spi<'d, M> { mode: Mode { polarity, phase }, bit_order, frequency, + miso_pull, } } @@ -406,7 +418,7 @@ impl<'d> Spi<'d, Blocking> { peri, new_pin!(sck, AFType::OutputPushPull, Speed::VeryHigh, config.sck_pull_mode()), new_pin!(mosi, AFType::OutputPushPull, Speed::VeryHigh), - new_pin!(miso, AFType::Input, Speed::VeryHigh), + new_pin!(miso, AFType::Input, Speed::VeryHigh, config.miso_pull), None, None, config, @@ -424,7 +436,7 @@ impl<'d> Spi<'d, Blocking> { peri, new_pin!(sck, AFType::OutputPushPull, Speed::VeryHigh, config.sck_pull_mode()), None, - new_pin!(miso, AFType::Input, Speed::VeryHigh), + new_pin!(miso, AFType::Input, Speed::VeryHigh, config.miso_pull), None, None, config,