#![no_main]
#![no_std]
use cortex_m_rt::entry;
use critical_section::with;
use hal::{
clocks::Clocks,
dma::{self, Dma, DmaChannel, DmaInput, DmaInterrupt, DmaPeriph, DmaWriteBuf},
gpio::{self, Pin, PinMode, Port},
low_power,
pac::{self, interrupt},
prelude::*,
spi::{self, BaudRate, Spi, SpiConfig, SpiMode},
};
static mut SPI_READ_BUF: [u8; 4] = [0; 4];
static mut SPI_WRITE_BUF: [u8; 4] = [0x69, 0, 0, 0];
make_globals!((SPI, Spi<SPI1>));
#[entry]
fn main() -> ! {
let mut cp = cortex_m::Peripherals::take().unwrap();
let mut dp = pac::Peripherals::take().unwrap();
let clock_cfg = Clocks::default();
clock_cfg.setup().unwrap();
let _sck = Pin::new(Port::A, 5, PinMode::Alt(5));
let _miso = Pin::new(Port::A, 6, PinMode::Alt(5));
let _mosi = Pin::new(Port::A, 7, PinMode::Alt(5));
let mut cs = Pin::new(Port::A, 1, PinMode::Output);
let spi_cfg = SpiConfig {
mode: SpiMode::mode1(),
..Default::default()
};
let mut spi = Spi::new(
dp.SPI1,
spi_cfg,
BaudRate::Div32, );
let mut dma = Dma::new(&mut dp.DMA1, &dp.RCC);
dma::mux(DmaPeriph::Dma2, DmaChannel::C1, DmaInput::Spi1Tx);
dma::mux(DmaPeriph::Dma2, DmaChannel::C2, DmaInput::Spi1Rx);
cs.set_low();
unsafe {
spi.transfer_dma(
&SPI_WRITE_BUF,
&mut SPI_READ_BUF, DmaChannel::C1, DmaChannel::C2, Default::default(), Default::default(), DmaPeriph::Dma2,
);
}
let mut write_buf = [0x80, 100];
let mut read_buf = [0x9f, 0, 0, 0];
spi.write(&write_buf).ok();
spi.transfer(&mut read_buf).ok();
defmt::println!("Data: {}", read_buf);
init_globals!((DMA, dma), (SPI, spi));
setup_nvic!([(DMA1_CH2, 1)], cp);
loop {
low_power::sleep_now();
}
}
#[interrupt]
fn DMA1_CH2() {
dma::clear_interrupt(
DmaPeriph::Dma2,
DmaChannel::C2,
DmaInterrupt::TransferComplete,
);
with(|cs| {
defmt::println!("SPI DMA read complete");
access_global!(SPI, spi, cs);
spi.stop_dma(DmaChannel::C1, Some(DmaChannel::C2), DmaPeriph::Dma2);
spi.cleanup_dma(DmaPeriph::Dma2, DmaChannel::C1, Some(DmaChannel::C2));
unsafe {
println!("Data read: {:?}", SPI_READ_BUF);
}
gpio::set_high(Port::A, 1);
})
}
#[defmt::panic_handler]
fn panic() -> ! {
cortex_m::asm::udf()
}