Merge pull request #53 from kbleeke/send-status
use send status feature of cyw43 instead of manually checking status
This commit is contained in:
commit
d918919cb2
@ -215,16 +215,26 @@ impl MySpi {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl cyw43::SpiBusCyw43 for MySpi {
|
impl cyw43::SpiBusCyw43 for MySpi {
|
||||||
async fn cmd_write(&mut self, write: &[u32]) {
|
async fn cmd_write(&mut self, write: &[u32]) -> u32 {
|
||||||
self.cs.set_low();
|
self.cs.set_low();
|
||||||
self.write(write).await;
|
self.write(write).await;
|
||||||
|
|
||||||
|
let mut status = 0;
|
||||||
|
self.read(slice::from_mut(&mut status)).await;
|
||||||
|
|
||||||
self.cs.set_high();
|
self.cs.set_high();
|
||||||
|
status
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn cmd_read(&mut self, write: u32, read: &mut [u32]) {
|
async fn cmd_read(&mut self, write: u32, read: &mut [u32]) -> u32 {
|
||||||
self.cs.set_low();
|
self.cs.set_low();
|
||||||
self.write(slice::from_ref(&write)).await;
|
self.write(slice::from_ref(&write)).await;
|
||||||
self.read(read).await;
|
self.read(read).await;
|
||||||
|
|
||||||
|
let mut status = 0;
|
||||||
|
self.read(slice::from_mut(&mut status)).await;
|
||||||
|
|
||||||
self.cs.set_high();
|
self.cs.set_high();
|
||||||
|
status
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -108,7 +108,7 @@ where
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn write(&mut self, write: &[u32]) {
|
pub async fn write(&mut self, write: &[u32]) -> u32 {
|
||||||
self.sm.set_enable(false);
|
self.sm.set_enable(false);
|
||||||
let write_bits = write.len() * 32 - 1;
|
let write_bits = write.len() * 32 - 1;
|
||||||
let read_bits = 31;
|
let read_bits = 31;
|
||||||
@ -125,15 +125,14 @@ where
|
|||||||
|
|
||||||
self.sm.dma_push(dma.reborrow(), write).await;
|
self.sm.dma_push(dma.reborrow(), write).await;
|
||||||
|
|
||||||
let mut status = 0;
|
let status = self.sm.wait_pull().await;
|
||||||
self.sm.dma_pull(dma, slice::from_mut(&mut status)).await;
|
status
|
||||||
defmt::trace!("{:#08x}", status);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn cmd_read(&mut self, cmd: u32, read: &mut [u32]) {
|
pub async fn cmd_read(&mut self, cmd: u32, read: &mut [u32]) -> u32 {
|
||||||
self.sm.set_enable(false);
|
self.sm.set_enable(false);
|
||||||
let write_bits = 31;
|
let write_bits = 31;
|
||||||
let read_bits = read.len() * 32 - 1;
|
let read_bits = read.len() * 32 + 32 - 1;
|
||||||
|
|
||||||
defmt::trace!("write={} read={}", write_bits, read_bits);
|
defmt::trace!("write={} read={}", write_bits, read_bits);
|
||||||
|
|
||||||
@ -147,6 +146,9 @@ where
|
|||||||
|
|
||||||
self.sm.dma_push(dma.reborrow(), slice::from_ref(&cmd)).await;
|
self.sm.dma_push(dma.reborrow(), slice::from_ref(&cmd)).await;
|
||||||
self.sm.dma_pull(dma, read).await;
|
self.sm.dma_pull(dma, read).await;
|
||||||
|
|
||||||
|
let status = self.sm.wait_pull().await;
|
||||||
|
status
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -156,16 +158,18 @@ where
|
|||||||
SM: PioStateMachine,
|
SM: PioStateMachine,
|
||||||
DMA: Channel,
|
DMA: Channel,
|
||||||
{
|
{
|
||||||
async fn cmd_write(&mut self, write: &[u32]) {
|
async fn cmd_write(&mut self, write: &[u32]) -> u32 {
|
||||||
self.cs.set_low();
|
self.cs.set_low();
|
||||||
self.write(write).await;
|
let status = self.write(write).await;
|
||||||
self.cs.set_high();
|
self.cs.set_high();
|
||||||
|
status
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn cmd_read(&mut self, write: u32, read: &mut [u32]) {
|
async fn cmd_read(&mut self, write: u32, read: &mut [u32]) -> u32 {
|
||||||
self.cs.set_low();
|
self.cs.set_low();
|
||||||
self.cmd_read(write, read).await;
|
let status = self.cmd_read(write, read).await;
|
||||||
self.cs.set_high();
|
self.cs.set_high();
|
||||||
|
status
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn wait_for_event(&mut self) {
|
async fn wait_for_event(&mut self) {
|
||||||
|
33
src/bus.rs
33
src/bus.rs
@ -12,14 +12,14 @@ use crate::consts::*;
|
|||||||
pub trait SpiBusCyw43 {
|
pub trait SpiBusCyw43 {
|
||||||
/// Issues a write command on the bus
|
/// Issues a write command on the bus
|
||||||
/// First 32 bits of `word` are expected to be a cmd word
|
/// First 32 bits of `word` are expected to be a cmd word
|
||||||
async fn cmd_write(&mut self, write: &[u32]);
|
async fn cmd_write(&mut self, write: &[u32]) -> u32;
|
||||||
|
|
||||||
/// Issues a read command on the bus
|
/// Issues a read command on the bus
|
||||||
/// `write` is expected to be a 32 bit cmd word
|
/// `write` is expected to be a 32 bit cmd word
|
||||||
/// `read` will contain the response of the device
|
/// `read` will contain the response of the device
|
||||||
/// Backplane reads have a response delay that produces one extra unspecified word at the beginning of `read`.
|
/// Backplane reads have a response delay that produces one extra unspecified word at the beginning of `read`.
|
||||||
/// Callers that want to read `n` word from the backplane, have to provide a slice that is `n+1` words long.
|
/// Callers that want to read `n` word from the backplane, have to provide a slice that is `n+1` words long.
|
||||||
async fn cmd_read(&mut self, write: u32, read: &mut [u32]);
|
async fn cmd_read(&mut self, write: u32, read: &mut [u32]) -> u32;
|
||||||
|
|
||||||
/// Wait for events from the Device. A typical implementation would wait for the IRQ pin to be high.
|
/// Wait for events from the Device. A typical implementation would wait for the IRQ pin to be high.
|
||||||
/// The default implementation always reports ready, resulting in active polling of the device.
|
/// The default implementation always reports ready, resulting in active polling of the device.
|
||||||
@ -32,6 +32,7 @@ pub(crate) struct Bus<PWR, SPI> {
|
|||||||
backplane_window: u32,
|
backplane_window: u32,
|
||||||
pwr: PWR,
|
pwr: PWR,
|
||||||
spi: SPI,
|
spi: SPI,
|
||||||
|
status: u32,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<PWR, SPI> Bus<PWR, SPI>
|
impl<PWR, SPI> Bus<PWR, SPI>
|
||||||
@ -44,6 +45,7 @@ where
|
|||||||
backplane_window: 0xAAAA_AAAA,
|
backplane_window: 0xAAAA_AAAA,
|
||||||
pwr,
|
pwr,
|
||||||
spi,
|
spi,
|
||||||
|
status: 0,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -70,8 +72,11 @@ where
|
|||||||
trace!("{:#010b}", (val & 0xff));
|
trace!("{:#010b}", (val & 0xff));
|
||||||
|
|
||||||
// 32-bit word length, little endian (which is the default endianess).
|
// 32-bit word length, little endian (which is the default endianess).
|
||||||
self.write32_swapped(REG_BUS_CTRL, WORD_LENGTH_32 | HIGH_SPEED | INTERRUPT_HIGH | WAKE_UP)
|
self.write32_swapped(
|
||||||
.await;
|
REG_BUS_CTRL,
|
||||||
|
WORD_LENGTH_32 | HIGH_SPEED | INTERRUPT_HIGH | WAKE_UP | STATUS_ENABLE,
|
||||||
|
)
|
||||||
|
.await;
|
||||||
|
|
||||||
let val = self.read8(FUNC_BUS, REG_BUS_CTRL).await;
|
let val = self.read8(FUNC_BUS, REG_BUS_CTRL).await;
|
||||||
trace!("{:#b}", val);
|
trace!("{:#b}", val);
|
||||||
@ -88,7 +93,7 @@ where
|
|||||||
let cmd = cmd_word(READ, INC_ADDR, FUNC_WLAN, 0, len_in_u8);
|
let cmd = cmd_word(READ, INC_ADDR, FUNC_WLAN, 0, len_in_u8);
|
||||||
let len_in_u32 = (len_in_u8 as usize + 3) / 4;
|
let len_in_u32 = (len_in_u8 as usize + 3) / 4;
|
||||||
|
|
||||||
self.spi.cmd_read(cmd, &mut buf[..len_in_u32]).await;
|
self.status = self.spi.cmd_read(cmd, &mut buf[..len_in_u32]).await;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn wlan_write(&mut self, buf: &[u32]) {
|
pub async fn wlan_write(&mut self, buf: &[u32]) {
|
||||||
@ -98,7 +103,7 @@ where
|
|||||||
cmd_buf[0] = cmd;
|
cmd_buf[0] = cmd;
|
||||||
cmd_buf[1..][..buf.len()].copy_from_slice(buf);
|
cmd_buf[1..][..buf.len()].copy_from_slice(buf);
|
||||||
|
|
||||||
self.spi.cmd_write(&cmd_buf).await;
|
self.status = self.spi.cmd_write(&cmd_buf).await;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(unused)]
|
#[allow(unused)]
|
||||||
@ -124,7 +129,7 @@ where
|
|||||||
let cmd = cmd_word(READ, INC_ADDR, FUNC_BACKPLANE, window_offs, len as u32);
|
let cmd = cmd_word(READ, INC_ADDR, FUNC_BACKPLANE, window_offs, len as u32);
|
||||||
|
|
||||||
// round `buf` to word boundary, add one extra word for the response delay
|
// round `buf` to word boundary, add one extra word for the response delay
|
||||||
self.spi.cmd_read(cmd, &mut buf[..(len + 3) / 4 + 1]).await;
|
self.status = self.spi.cmd_read(cmd, &mut buf[..(len + 3) / 4 + 1]).await;
|
||||||
|
|
||||||
// when writing out the data, we skip the response-delay byte
|
// when writing out the data, we skip the response-delay byte
|
||||||
data[..len].copy_from_slice(&slice8_mut(&mut buf[1..])[..len]);
|
data[..len].copy_from_slice(&slice8_mut(&mut buf[1..])[..len]);
|
||||||
@ -157,7 +162,7 @@ where
|
|||||||
let cmd = cmd_word(WRITE, INC_ADDR, FUNC_BACKPLANE, window_offs, len as u32);
|
let cmd = cmd_word(WRITE, INC_ADDR, FUNC_BACKPLANE, window_offs, len as u32);
|
||||||
buf[0] = cmd;
|
buf[0] = cmd;
|
||||||
|
|
||||||
self.spi.cmd_write(&buf[..(len + 3) / 4 + 1]).await;
|
self.status = self.spi.cmd_write(&buf[..(len + 3) / 4 + 1]).await;
|
||||||
|
|
||||||
// Advance ptr.
|
// Advance ptr.
|
||||||
addr += len as u32;
|
addr += len as u32;
|
||||||
@ -273,7 +278,7 @@ where
|
|||||||
// if we are reading from the backplane, we need an extra word for the response delay
|
// if we are reading from the backplane, we need an extra word for the response delay
|
||||||
let len = if func == FUNC_BACKPLANE { 2 } else { 1 };
|
let len = if func == FUNC_BACKPLANE { 2 } else { 1 };
|
||||||
|
|
||||||
self.spi.cmd_read(cmd, &mut buf[..len]).await;
|
self.status = self.spi.cmd_read(cmd, &mut buf[..len]).await;
|
||||||
|
|
||||||
// if we read from the backplane, the result is in the second word, after the response delay
|
// if we read from the backplane, the result is in the second word, after the response delay
|
||||||
if func == FUNC_BACKPLANE {
|
if func == FUNC_BACKPLANE {
|
||||||
@ -286,7 +291,7 @@ where
|
|||||||
async fn writen(&mut self, func: u32, addr: u32, val: u32, len: u32) {
|
async fn writen(&mut self, func: u32, addr: u32, val: u32, len: u32) {
|
||||||
let cmd = cmd_word(WRITE, INC_ADDR, func, addr, len);
|
let cmd = cmd_word(WRITE, INC_ADDR, func, addr, len);
|
||||||
|
|
||||||
self.spi.cmd_write(&[cmd, val]).await;
|
self.status = self.spi.cmd_write(&[cmd, val]).await;
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn read32_swapped(&mut self, addr: u32) -> u32 {
|
async fn read32_swapped(&mut self, addr: u32) -> u32 {
|
||||||
@ -294,7 +299,7 @@ where
|
|||||||
let cmd = swap16(cmd);
|
let cmd = swap16(cmd);
|
||||||
let mut buf = [0; 1];
|
let mut buf = [0; 1];
|
||||||
|
|
||||||
self.spi.cmd_read(cmd, &mut buf).await;
|
self.status = self.spi.cmd_read(cmd, &mut buf).await;
|
||||||
|
|
||||||
swap16(buf[0])
|
swap16(buf[0])
|
||||||
}
|
}
|
||||||
@ -303,12 +308,16 @@ where
|
|||||||
let cmd = cmd_word(WRITE, INC_ADDR, FUNC_BUS, addr, 4);
|
let cmd = cmd_word(WRITE, INC_ADDR, FUNC_BUS, addr, 4);
|
||||||
let buf = [swap16(cmd), swap16(val)];
|
let buf = [swap16(cmd), swap16(val)];
|
||||||
|
|
||||||
self.spi.cmd_write(&buf).await;
|
self.status = self.spi.cmd_write(&buf).await;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn wait_for_event(&mut self) {
|
pub async fn wait_for_event(&mut self) {
|
||||||
self.spi.wait_for_event().await;
|
self.spi.wait_for_event().await;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn status(&self) -> u32 {
|
||||||
|
self.status
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn swap16(x: u32) -> u32 {
|
fn swap16(x: u32) -> u32 {
|
||||||
|
@ -16,6 +16,7 @@ pub(crate) const WORD_LENGTH_32: u32 = 0x1;
|
|||||||
pub(crate) const HIGH_SPEED: u32 = 0x10;
|
pub(crate) const HIGH_SPEED: u32 = 0x10;
|
||||||
pub(crate) const INTERRUPT_HIGH: u32 = 1 << 5;
|
pub(crate) const INTERRUPT_HIGH: u32 = 1 << 5;
|
||||||
pub(crate) const WAKE_UP: u32 = 1 << 7;
|
pub(crate) const WAKE_UP: u32 = 1 << 7;
|
||||||
|
pub(crate) const STATUS_ENABLE: u32 = 0x10000;
|
||||||
|
|
||||||
// SPI_STATUS_REGISTER bits
|
// SPI_STATUS_REGISTER bits
|
||||||
pub(crate) const STATUS_DATA_NOT_AVAILABLE: u32 = 0x00000001;
|
pub(crate) const STATUS_DATA_NOT_AVAILABLE: u32 = 0x00000001;
|
||||||
|
@ -315,10 +315,7 @@ where
|
|||||||
/// Handle F2 events while status register is set
|
/// Handle F2 events while status register is set
|
||||||
async fn check_status(&mut self, buf: &mut [u32; 512]) {
|
async fn check_status(&mut self, buf: &mut [u32; 512]) {
|
||||||
loop {
|
loop {
|
||||||
let mut status = 0xFFFF_FFFF;
|
let status = self.bus.status();
|
||||||
while status == 0xFFFF_FFFF {
|
|
||||||
status = self.bus.read32(FUNC_BUS, REG_BUS_STATUS).await;
|
|
||||||
}
|
|
||||||
trace!("check status{}", FormatStatus(status));
|
trace!("check status{}", FormatStatus(status));
|
||||||
|
|
||||||
if status & STATUS_F2_PKT_AVAILABLE != 0 {
|
if status & STATUS_F2_PKT_AVAILABLE != 0 {
|
||||||
|
Loading…
Reference in New Issue
Block a user