humpback-dds/src/spi_slave.rs

58 lines
1.6 KiB
Rust

use embedded_hal::{
blocking::spi::Transfer,
digital::v2::OutputPin,
};
use core::marker::PhantomData;
use crate::{DoOnGetRefMutData, Error, SelectChip};
pub struct SPISlave<'a, DEV: 'a, SPI, CS0, CS1, CS2> (
&'a DEV,
u8,
PhantomData<(SPI, CS0, CS1, CS2)>,
);
pub struct Parts<'a, DEV: 'a, SPI, CS0, CS1, CS2> {
pub spi1: SPISlave<'a, DEV, SPI, CS0, CS1, CS2>,
pub spi2: SPISlave<'a, DEV, SPI, CS0, CS1, CS2>,
pub spi3: SPISlave<'a, DEV, SPI, CS0, CS1, CS2>,
pub spi4: SPISlave<'a, DEV, SPI, CS0, CS1, CS2>,
pub spi5: SPISlave<'a, DEV, SPI, CS0, CS1, CS2>,
pub spi6: SPISlave<'a, DEV, SPI, CS0, CS1, CS2>,
pub spi7: SPISlave<'a, DEV, SPI, CS0, CS1, CS2>,
}
impl<'a, DEV, SPI, CS0, CS1, CS2> Parts<'a, DEV, SPI, CS0, CS1, CS2> {
pub(crate) fn new(cpld: &'a DEV) -> Self {
Parts {
spi1: SPISlave(&cpld, 1, PhantomData),
spi2: SPISlave(&cpld, 2, PhantomData),
spi3: SPISlave(&cpld, 3, PhantomData),
spi4: SPISlave(&cpld, 4, PhantomData),
spi5: SPISlave(&cpld, 5, PhantomData),
spi6: SPISlave(&cpld, 6, PhantomData),
spi7: SPISlave(&cpld, 7, PhantomData),
}
}
}
impl<'a, DEV, SPI, CS0, CS1, CS2, E> Transfer<u8> for SPISlave<'a, DEV, SPI, CS0, CS1, CS2>
where
CS2: OutputPin,
CS1: OutputPin,
CS0: OutputPin,
DEV: DoOnGetRefMutData<SPI, CS0, CS1, CS2>,
SPI: Transfer<u8, Error = E>,
{
type Error = Error<E>;
fn transfer<'w>(&mut self, words: &'w mut[u8]) -> Result<&'w [u8], Self::Error> {
self.0.do_on_get_ref_mut_data(move |mut dev| {
dev.select_chip(self.1);
let result = dev.spi.transfer(words).map_err(Error::SPI);
dev.select_chip(0);
result
})
}
}