diff --git a/esp-hal/CHANGELOG.md b/esp-hal/CHANGELOG.md index f9a8a744da..2443bf2484 100644 --- a/esp-hal/CHANGELOG.md +++ b/esp-hal/CHANGELOG.md @@ -34,6 +34,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - GPIO ETM tasks and events now accept `InputSignal` and `OutputSignal` (#2427) - `spi::master::Config` and `{Spi, SpiDma, SpiDmaBus}::apply_config` (#2448) - `embassy_embedded_hal::SetConfig` is now implemented for `{Spi, SpiDma, SpiDmaBus}` (#2448) +- `slave::Spi::{with_mosi(), with_miso(), with_sclk(), with_cs()}` functions (#?) ### Changed @@ -55,6 +56,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - `spi::master::Spi::new()` no longer takes `frequency` and `mode` as a parameter. (#2448) - Peripheral interconnections via GPIO pins now use the GPIO matrix. (#2419) - The I2S driver has been moved to `i2s::master` (#2472) +- `slave::Spi` constructors no longer take pins (#?) ### Fixed diff --git a/esp-hal/MIGRATING-0.21.md b/esp-hal/MIGRATING-0.21.md index e803f1377e..9fbad463a3 100644 --- a/esp-hal/MIGRATING-0.21.md +++ b/esp-hal/MIGRATING-0.21.md @@ -84,7 +84,6 @@ drivers. It is now possible to execute half-duplex and full-duplex operations on - The `Spi::new_half_duplex` constructor has been removed. Use `new` (or `new_typed`) instead. - The `with_pins` methods have been removed. Use the individual `with_*` functions instead. - The `with_mosi` and `with_miso` functions now take input-output peripheral signals to support half-duplex mode. - > TODO(danielb): this means they are currently only usable with GPIO pins, but upcoming GPIO changes should allow using any output signal. ```diff - let mut spi = Spi::new_half_duplex(peripherals.SPI2, 100.kHz(), SpiMode::Mode0) @@ -131,6 +130,28 @@ The `Spi<'_, SPI, HalfDuplexMode>::read` and `Spi<'_, SPI, HalfDuplexMode>::writ .unwrap(); ``` +## Slave-mode SPI + +### Driver construction + +The constructors no longer accept pins. Use the `with_pin_name` setters instead. + +```diff + let mut spi = Spi::new( + peripherals.SPI2, +- sclk, +- mosi, +- miso, +- cs, + SpiMode::Mode0, +-); ++) ++.with_sclk(sclk) ++.with_mosi(mosi) ++.with_miso(miso) ++.with_cs(cs); +``` + ## UART event listening The following functions have been removed: diff --git a/esp-hal/src/spi/slave.rs b/esp-hal/src/spi/slave.rs index 0ffad8f7c9..84b71919d7 100644 --- a/esp-hal/src/spi/slave.rs +++ b/esp-hal/src/spi/slave.rs @@ -34,16 +34,20 @@ //! dma_buffers!(32000); //! let mut spi = Spi::new( //! peripherals.SPI2, -//! sclk, -//! mosi, -//! miso, -//! cs, //! SpiMode::Mode0, //! ) -//! .with_dma(dma_channel.configure( -//! false, -//! DmaPriority::Priority0, -//! ), rx_descriptors, tx_descriptors); +//! .with_sclk(sclk) +//! .with_mosi(mosi) +//! .with_miso(miso) +//! .with_cs(cs) +//! .with_dma( +//! dma_channel.configure( +//! false, +//! DmaPriority::Priority0, +//! ), +//! rx_descriptors, +//! tx_descriptors, +//! ); //! //! let mut receive = rx_buffer; //! let mut send = tx_buffer; @@ -110,13 +114,9 @@ impl<'d> Spi<'d, Blocking> { CS: PeripheralInput, >( spi: impl Peripheral

+ 'd, - sclk: impl Peripheral

+ 'd, - mosi: impl Peripheral

+ 'd, - miso: impl Peripheral

+ 'd, - cs: impl Peripheral

+ 'd, mode: SpiMode, ) -> Spi<'d, Blocking> { - Self::new_typed(spi.map_into(), sclk, mosi, miso, cs, mode) + Self::new_typed(spi.map_into(), mode) } } @@ -125,55 +125,57 @@ where T: Instance, { /// Constructs an SPI instance in 8bit dataframe mode. - pub fn new_typed< - SCK: PeripheralInput, - MOSI: PeripheralInput, - MISO: PeripheralOutput, - CS: PeripheralInput, - >( - spi: impl Peripheral

+ 'd, - sclk: impl Peripheral

+ 'd, - mosi: impl Peripheral

+ 'd, - miso: impl Peripheral

+ 'd, - cs: impl Peripheral

+ 'd, - mode: SpiMode, - ) -> Spi<'d, M, T> { - crate::into_mapped_ref!(sclk, mosi, miso, cs); - - let this = Self::new_internal(spi, mode); - - // TODO: with_pins et. al. - sclk.enable_input(true, private::Internal); - this.spi.info().sclk.connect_to(sclk); - - mosi.enable_input(true, private::Internal); - this.spi.info().mosi.connect_to(mosi); - - miso.set_to_push_pull_output(private::Internal); - this.spi.info().miso.connect_to(miso); - - cs.enable_input(true, private::Internal); - this.spi.info().cs.connect_to(cs); - - this - } - - pub(crate) fn new_internal(spi: impl Peripheral

+ 'd, mode: SpiMode) -> Spi<'d, M, T> { + pub fn new_typed(spi: impl Peripheral

+ 'd, mode: SpiMode) -> Spi<'d, M, T> { crate::into_ref!(spi); - let spi = Spi { + let this = Spi { spi, data_mode: mode, _mode: PhantomData, }; - PeripheralClockControl::reset(spi.spi.info().peripheral); - PeripheralClockControl::enable(spi.spi.info().peripheral); + PeripheralClockControl::reset(this.spi.info().peripheral); + PeripheralClockControl::enable(this.spi.info().peripheral); + + this.spi.info().init(); + this.spi.info().set_data_mode(mode, false); - spi.spi.info().init(); - spi.spi.info().set_data_mode(mode, false); + this.with_mosi(NoPin) + .with_miso(NoPin) + .with_sck(NoPin) + .with_cs(NoPin) + } + + /// Assign the SCLK (Serial Clock) pin for the SPI instance. + pub fn with_sclk(self, sclk: impl Peripheral

+ 'd) -> Self { + crate::into_mapped_ref!(sclk); + sclk.enable_input(true, private::Internal); + self.spi.info().sclk.connect_to(sclk); + self + } - spi + /// Assign the MOSI (Master Out Slave In) pin for the SPI instance. + pub fn with_mosi(self, mosi: impl Peripheral

+ 'd) -> Self { + crate::into_mapped_ref!(mosi); + mosi.enable_input(true, private::Internal); + self.spi.info().mosi.connect_to(mosi); + self + } + + /// Assign the MISO (Master In Slave Out) pin for the SPI instance. + pub fn with_miso(self, miso: impl Peripheral

+ 'd) -> Self { + crate::into_mapped_ref!(miso); + miso.set_to_push_pull_output(private::Internal); + self.spi.info().miso.connect_to(miso); + self + } + + /// Assign the CS (Chip Select) pin for the SPI instance. + pub fn with_cs(self, cs: impl Peripheral

+ 'd) -> Self { + crate::into_mapped_ref!(cs); + cs.enable_input(true, private::Internal); + self.spi.info().cs.connect_to(cs); + self } } diff --git a/examples/src/bin/spi_slave_dma.rs b/examples/src/bin/spi_slave_dma.rs index 5352c71db8..27874423a2 100644 --- a/examples/src/bin/spi_slave_dma.rs +++ b/examples/src/bin/spi_slave_dma.rs @@ -67,19 +67,16 @@ fn main() -> ! { let (rx_buffer, rx_descriptors, tx_buffer, tx_descriptors) = dma_buffers!(32000); - let mut spi = Spi::new( - peripherals.SPI2, - slave_sclk, - slave_mosi, - slave_miso, - slave_cs, - SpiMode::Mode0, - ) - .with_dma( - dma_channel.configure(false, DmaPriority::Priority0), - tx_descriptors, - rx_descriptors, - ); + let mut spi = Spi::new(peripherals.SPI2, SpiMode::Mode0) + .with_sclk(slave_sclk) + .with_mosi(slave_mosi) + .with_miso(slave_miso) + .with_cs(slave_cs) + .with_dma( + dma_channel.configure(false, DmaPriority::Priority0), + tx_descriptors, + rx_descriptors, + ); let delay = Delay::new(); diff --git a/hil-test/tests/spi_slave.rs b/hil-test/tests/spi_slave.rs index 6d8c1aeaf1..5012ad211d 100644 --- a/hil-test/tests/spi_slave.rs +++ b/hil-test/tests/spi_slave.rs @@ -130,7 +130,11 @@ mod tests { let miso = unsafe { miso_gpio.clone_unchecked() }.into_peripheral_output(); Context { - spi: Spi::new(peripherals.SPI2, sclk, mosi, miso, cs, SpiMode::Mode1), + spi: Spi::new(peripherals.SPI2, SpiMode::Mode1) + .with_sclk(sclk) + .with_mosi(mosi) + .with_miso(miso) + .with_cs(cs), bitbang_spi: BitbangSpi::new(sclk_gpio, mosi_gpio, miso_gpio, cs_gpio), dma_channel, }