esp_hal/spi/mod.rs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115
//! Serial Peripheral Interface (SPI)
//!
//! ## Overview
//! The Serial Peripheral Interface (SPI) is a synchronous serial interface
//! useful for communication with external peripherals.
//!
//! ## Configuration
//! This peripheral is capable of operating in either master or slave mode. For
//! more information on these modes, please refer to the documentation in their
//! respective modules.
use crate::dma::{DmaEligible, DmaError};
pub mod master;
pub mod slave;
/// SPI errors
#[derive(Debug, Clone, Copy, PartialEq)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
pub enum Error {
/// Error occurred due to a DMA-related issue.
DmaError(DmaError),
/// Error indicating that the maximum DMA transfer size was exceeded.
MaxDmaTransferSizeExceeded,
/// Error indicating that the FIFO size was exceeded during SPI
/// communication.
FifoSizeExeeded,
/// Error indicating that the operation is unsupported by the current
/// implementation.
Unsupported,
/// An unknown error occurred during SPI communication.
Unknown,
}
impl From<DmaError> for Error {
fn from(value: DmaError) -> Self {
Error::DmaError(value)
}
}
impl embedded_hal::spi::Error for Error {
fn kind(&self) -> embedded_hal::spi::ErrorKind {
embedded_hal::spi::ErrorKind::Other
}
}
/// SPI communication modes, defined by clock polarity (CPOL) and clock phase
/// (CPHA).
///
/// These modes control the clock signal's idle state and when data is sampled
/// and shifted.
#[derive(Debug, Clone, Copy, PartialEq)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
pub enum SpiMode {
/// Mode 0 (CPOL = 0, CPHA = 0): Clock is low when idle, data is captured on
/// the rising edge and propagated on the falling edge.
Mode0,
/// Mode 1 (CPOL = 0, CPHA = 1): Clock is low when idle, data is captured on
/// the falling edge and propagated on the rising edge.
Mode1,
/// Mode 2 (CPOL = 1, CPHA = 0): Clock is high when idle, data is captured
/// on the falling edge and propagated on the rising edge.
Mode2,
/// Mode 3 (CPOL = 1, CPHA = 1): Clock is high when idle, data is captured
/// on the rising edge and propagated on the falling edge.
Mode3,
}
/// SPI Bit Order
#[derive(Debug, Clone, Copy, PartialEq)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
pub enum SpiBitOrder {
/// Most Significant Bit (MSB) is transmitted first.
MSBFirst,
/// Least Significant Bit (LSB) is transmitted first.
LSBFirst,
}
/// SPI data mode
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
pub enum SpiDataMode {
/// `Single` Data Mode - 1 bit, 2 wires.
Single,
/// `Dual` Data Mode - 2 bit, 2 wires
Dual,
/// `Quad` Data Mode - 4 bit, 4 wires
Quad,
}
crate::any_peripheral! {
/// Any SPI peripheral.
pub peripheral AnySpi {
#[cfg(spi2)]
Spi2(crate::peripherals::SPI2),
#[cfg(spi3)]
Spi3(crate::peripherals::SPI3),
}
}
impl DmaEligible for AnySpi {
#[cfg(gdma)]
type Dma = crate::dma::AnyGdmaChannel;
#[cfg(pdma)]
type Dma = crate::dma::AnySpiDmaChannel;
fn dma_peripheral(&self) -> crate::dma::DmaPeripheral {
match &self.0 {
#[cfg(spi2)]
AnySpiInner::Spi2(_) => crate::dma::DmaPeripheral::Spi2,
#[cfg(spi3)]
AnySpiInner::Spi3(_) => crate::dma::DmaPeripheral::Spi3,
}
}
}