From 21186af3bf0e54b46f19d94ebdaa9b6652af6d55 Mon Sep 17 00:00:00 2001 From: Robin Mueller Date: Thu, 19 Sep 2024 18:37:44 +0200 Subject: [PATCH] somethings wrong.. --- bootloader/src/main.rs | 1 - va108xx-hal/src/spi.rs | 64 +++++++++++++++++++--------- vorago-reb1/examples/max11619-adc.rs | 10 +---- vorago-reb1/examples/nvm.rs | 6 --- vorago-reb1/src/m95m01.rs | 31 ++++++++------ 5 files changed, 63 insertions(+), 49 deletions(-) diff --git a/bootloader/src/main.rs b/bootloader/src/main.rs index bc28aba..8def221 100644 --- a/bootloader/src/main.rs +++ b/bootloader/src/main.rs @@ -105,7 +105,6 @@ fn main() -> ! { (RomSck, RomMiso, RomMosi), // These values are taken from the vorago bootloader app, don't want to experiment here.. SpiConfig::default().clk_cfg(SpiClkConfig::new(2, 4)), - None, ); let mut nvm = M95M01::new(ExclusiveDevice::new_no_delay(spi, dummy_pin::DummyPin::new_low()).unwrap()) diff --git a/va108xx-hal/src/spi.rs b/va108xx-hal/src/spi.rs index b9a1056..390eaea 100644 --- a/va108xx-hal/src/spi.rs +++ b/va108xx-hal/src/spi.rs @@ -17,7 +17,7 @@ use crate::{ PeripheralSelect, }; use core::{convert::Infallible, fmt::Debug, marker::PhantomData, ops::Deref}; -use embedded_hal::spi::Mode; +use embedded_hal::spi::{Mode, MODE_0}; //================================================================================================== // Defintions @@ -363,6 +363,12 @@ impl TransferConfigProvider for TransferConfigWithHwcs /// Configuration options for the whole SPI bus. See Programmer Guide p.92 for more details pub struct SpiConfig { clk: SpiClkConfig, + // SPI mode configuration + pub init_mode: Mode, + /// If this is enabled, all data in the FIFO is transmitted in a single frame unless + /// the BMSTOP bit is set on a dataword. A frame is defined as CSn being active for the + /// duration of multiple data words. Defaults to true. + pub blockmode: bool, /// By default, configure SPI for master mode (ms == false) ms: bool, /// Slave output disable. Useful if separate GPIO pins or decoders are used for CS control @@ -376,6 +382,8 @@ pub struct SpiConfig { impl Default for SpiConfig { fn default() -> Self { Self { + init_mode: MODE_0, + blockmode: true, // Default value is definitely valid. clk: SpiClkConfig::from_div(DEFAULT_CLK_DIV).unwrap(), ms: Default::default(), @@ -392,6 +400,16 @@ impl SpiConfig { self } + pub fn blockmode(mut self, enable: bool) -> Self { + self.blockmode = enable; + self + } + + pub fn mode(mut self, mode: Mode) -> Self { + self.init_mode = mode; + self + } + pub fn clk_cfg(mut self, clk_cfg: SpiClkConfig) -> Self { self.clk = clk_cfg; self @@ -599,28 +617,17 @@ where spi: SpiI, pins: (Sck, Miso, Mosi), spi_cfg: SpiConfig, - transfer_cfg: Option<&TransferConfig>, ) -> Self { enable_peripheral_clock(syscfg, SpiI::PERIPH_SEL); let SpiConfig { clk, + init_mode, + blockmode, ms, slave_output_disable, loopback_mode, master_delayer_capture, } = spi_cfg; - let mut init_mode = embedded_hal::spi::MODE_0; - let mut ss = 0; - let mut init_blockmode = false; - if let Some(transfer_cfg) = transfer_cfg { - if let Some(mode) = transfer_cfg.mode { - init_mode = mode; - } - if transfer_cfg.hw_cs != HwChipSelectId::Invalid { - ss = transfer_cfg.hw_cs as u8; - } - init_blockmode = transfer_cfg.blockmode; - } let (cpo_bit, cph_bit) = mode_to_cpo_cph_bit(init_mode); spi.ctrl0().write(|w| { @@ -639,8 +646,8 @@ where w.sod().bit(slave_output_disable); w.ms().bit(ms); w.mdlycap().bit(master_delayer_capture); - w.blockmode().bit(init_blockmode); - unsafe { w.ss().bits(ss) } + w.blockmode().bit(blockmode); + unsafe { w.ss().bits(0) } }); spi.clkprescale() .write(|w| unsafe { w.bits(clk.prescale_val as u32) }); @@ -658,7 +665,7 @@ where cfg: spi_cfg, sys_clk: sys_clk.into(), fill_word: Default::default(), - blockmode: init_blockmode, + blockmode, word: PhantomData, }, pins, @@ -685,15 +692,22 @@ where #[inline] pub fn spi(&self) -> &SpiI; + /// Configure the hardware chip select given a hardware chip select ID. #[inline] pub fn cfg_hw_cs(&mut self, hw_cs: HwChipSelectId); + /// Configure the hardware chip select given a physical hardware CS pin. #[inline] pub fn cfg_hw_cs_with_pin>(&mut self, _hwcs: &HwCs); + /// Disables the hardware chip select functionality. This can be used when performing + /// external chip select handling, for example with GPIO pins. #[inline] pub fn cfg_hw_cs_disable(&mut self); + /// Utility function to configure all relevant transfer parameters in one go. + /// This is useful if multiple devices with different clock and mode configurations + /// are connected to one bus. pub fn cfg_transfer>( &mut self, transfer_cfg: &TransferConfigWithHwcs ); @@ -769,6 +783,7 @@ where self.spi.perid().read().bits() } + /// Configure the hardware chip select given a hardware chip select ID. #[inline] pub fn cfg_hw_cs(&mut self, hw_cs: HwChipSelectId) { if hw_cs == HwChipSelectId::Invalid { @@ -783,11 +798,15 @@ where }); } + /// Configure the hardware chip select given a physical hardware CS pin. #[inline] pub fn cfg_hw_cs_with_pin>(&mut self, _: &HwCs) { self.cfg_hw_cs(HwCs::CS_ID); } + /// Disables the hardware chip select functionality. This can be used when performing + /// external chip select handling, for example with GPIO pins. + #[inline] pub fn cfg_hw_cs_disable(&mut self) { self.spi.ctrl1().modify(|_, w| { w.sod().set_bit(); @@ -795,6 +814,9 @@ where }); } + /// Utility function to configure all relevant transfer parameters in one go. + /// This is useful if multiple devices with different clock and mode configurations + /// are connected to one bus. pub fn cfg_transfer>( &mut self, transfer_cfg: &TransferConfigWithHwcs, @@ -966,7 +988,7 @@ where >::Error: core::fmt::Debug, { fn read(&mut self, words: &mut [Word]) -> Result<(), Self::Error> { - self.transfer_preparation(words)?; + //self.transfer_preparation(words)?; let mut current_read_idx = 0; let mut current_write_idx = self.initial_send_fifo_pumping_with_fill_words(words.len()); loop { @@ -986,7 +1008,7 @@ where } fn write(&mut self, words: &[Word]) -> Result<(), Self::Error> { - self.transfer_preparation(words)?; + // self.transfer_preparation(words)?; let mut current_write_idx = self.initial_send_fifo_pumping_with_words(words); while current_write_idx < words.len() { self.send_blocking(words[current_write_idx]); @@ -1000,7 +1022,7 @@ where } fn transfer(&mut self, read: &mut [Word], write: &[Word]) -> Result<(), Self::Error> { - self.transfer_preparation(write)?; + //self.transfer_preparation(write)?; let mut current_read_idx = 0; let mut current_write_idx = self.initial_send_fifo_pumping_with_words(write); while current_read_idx < read.len() || current_write_idx < write.len() { @@ -1018,7 +1040,7 @@ where } fn transfer_in_place(&mut self, words: &mut [Word]) -> Result<(), Self::Error> { - self.transfer_preparation(words)?; + //self.transfer_preparation(words)?; let mut current_read_idx = 0; let mut current_write_idx = self.initial_send_fifo_pumping_with_words(words); diff --git a/vorago-reb1/examples/max11619-adc.rs b/vorago-reb1/examples/max11619-adc.rs index 84c34de..15e0577 100644 --- a/vorago-reb1/examples/max11619-adc.rs +++ b/vorago-reb1/examples/max11619-adc.rs @@ -124,7 +124,7 @@ fn main() -> ! { } let pinsa = PinsA::new(&mut dp.sysconfig, None, dp.porta); - let spi_cfg = SpiConfig::default(); + let spi_cfg = SpiConfig::default().clk_cfg(SpiClkConfig::from_clk(SYS_CLK, 3.MHz()).unwrap()); let (sck, mosi, miso) = ( pinsa.pa20.into_funsel_2(), pinsa.pa19.into_funsel_2(), @@ -143,19 +143,13 @@ fn main() -> ! { .set_high() .expect("Setting accelerometer chip select high failed"); - let transfer_cfg = TransferConfigWithHwcs::new_no_hw_cs( - Some(SpiClkConfig::from_clk(SYS_CLK, 3.MHz()).unwrap()), - Some(spi::MODE_0), - true, - false, - ); + let transfer_cfg = TransferConfigWithHwcs::new_no_hw_cs(None, Some(spi::MODE_0), true, false); let spi = Spi::new( &mut dp.sysconfig, 50.MHz(), dp.spib, (sck, miso, mosi), spi_cfg, - Some(&transfer_cfg.downgrade()), ) .downgrade(); let delay_provider = CountDownTimer::new(&mut dp.sysconfig, 50.MHz(), dp.tim1); diff --git a/vorago-reb1/examples/nvm.rs b/vorago-reb1/examples/nvm.rs index 8f6e083..3e19ddc 100644 --- a/vorago-reb1/examples/nvm.rs +++ b/vorago-reb1/examples/nvm.rs @@ -30,15 +30,10 @@ fn main() -> ! { (RomSck, RomMiso, RomMosi), // These values are taken from the vorago bootloader app, don't want to experiment here.. SpiConfig::default().clk_cfg(SpiClkConfig::new(2, 4)), - None, ); - spi.cfg_mode(MODE_0); - spi.cfg_hw_cs(va108xx_hal::spi::HwChipSelectId::Id0); - spi.spi().ctrl1().modify(|_, w| w.blockmode().set_bit()); let mut read_buf: [u8; 2] = [0; 2]; spi.transfer(&mut read_buf, &[RDSR, 0]); rprintln!("read buf {:?}", read_buf); - /* let mut nvm = M95M01::new(ExclusiveDevice::new_no_delay(spi, dummy_pin::DummyPin::new_low()).unwrap()) .expect("creating NVM structure failed"); @@ -56,6 +51,5 @@ fn main() -> ! { nvm.write(0x4000, &write_buf).unwrap(); nvm.read(0x4000, &mut read_buf[0..4]).unwrap(); assert_eq!(&read_buf[0..4], write_buf); - */ loop {} } diff --git a/vorago-reb1/src/m95m01.rs b/vorago-reb1/src/m95m01.rs index e43b4ff..e959e3e 100644 --- a/vorago-reb1/src/m95m01.rs +++ b/vorago-reb1/src/m95m01.rs @@ -1,5 +1,5 @@ use core::fmt::Debug; -use embedded_hal::spi::SpiDevice; +use embedded_hal::spi::{Operation, SpiDevice}; bitfield::bitfield! { pub struct StatusReg(u8); @@ -97,13 +97,15 @@ where pub fn write(&mut self, address: u32, data: &[u8]) -> Result<(), Spi::Error> { nb::block!(self.writes_are_done())?; self.write_enable()?; - self.spi.write(&[ - WRITE, - ((address >> 16) & 0xff) as u8, - ((address >> 8) & 0xff) as u8, - (address & 0xff) as u8, + self.spi.transaction(&mut [ + Operation::Write(&[ + WRITE, + ((address >> 16) & 0xff) as u8, + ((address >> 8) & 0xff) as u8, + (address & 0xff) as u8, + ]), + Operation::Write(data), ])?; - self.spi.write(data)?; Ok(()) } @@ -112,13 +114,16 @@ where return Err(Error::BufTooShort); } nb::block!(self.writes_are_done())?; - self.spi.write(&[ - READ, - ((address >> 16) & 0xff) as u8, - ((address >> 8) & 0xff) as u8, - (address & 0xff) as u8, + + self.spi.transaction(&mut [ + Operation::Write(&[ + READ, + ((address >> 16) & 0xff) as u8, + ((address >> 8) & 0xff) as u8, + (address & 0xff) as u8, + ]), + Operation::Read(buf), ])?; - self.spi.read(buf)?; Ok(()) }