Skip to content

Commit d9a3f0b

Browse files
committed
Implement FullDuplex for SPI and add check_errors method
check_errors only checks for Overrun, CRC error and ModeFault flags.
1 parent 2bb8bb9 commit d9a3f0b

File tree

1 file changed

+80
-22
lines changed

1 file changed

+80
-22
lines changed

src/spi.rs

+80-22
Original file line numberDiff line numberDiff line change
@@ -365,17 +365,27 @@ where
365365
fn check_read(&mut self) -> nb::Result<(), Error> {
366366
let sr = self.spi.sr.read();
367367

368-
Err(if sr.ovr().bit_is_set() {
369-
nb::Error::Other(Error::Overrun)
368+
self.check_errors()?;
369+
370+
if !sr.rxne().bit_is_set() {
371+
Err(nb::Error::WouldBlock)
372+
} else {
373+
Ok(())
374+
}
375+
}
376+
377+
fn check_errors(&mut self) -> Result<(), Error> {
378+
let sr = self.spi.sr.read();
379+
380+
if sr.ovr().bit_is_set() {
381+
Err(Error::Overrun)
370382
} else if sr.modf().bit_is_set() {
371-
nb::Error::Other(Error::ModeFault)
383+
Err(Error::ModeFault)
372384
} else if sr.crcerr().bit_is_set() {
373-
nb::Error::Other(Error::Crc)
374-
} else if sr.rxne().bit_is_set() {
375-
return Ok(());
385+
Err(Error::Crc)
376386
} else {
377-
nb::Error::WouldBlock
378-
})
387+
Ok(())
388+
}
379389
}
380390

381391
fn send_buffer_size(&mut self) -> u8 {
@@ -394,17 +404,15 @@ where
394404
fn check_send(&mut self) -> nb::Result<(), Error> {
395405
let sr = self.spi.sr.read();
396406

397-
Err(if sr.ovr().bit_is_set() {
398-
nb::Error::Other(Error::Overrun)
399-
} else if sr.modf().bit_is_set() {
400-
nb::Error::Other(Error::ModeFault)
401-
} else if sr.crcerr().bit_is_set() {
402-
nb::Error::Other(Error::Crc)
403-
} else if sr.txe().bit_is_set() {
404-
return Ok(());
407+
if let Err(e) = self.check_errors() {
408+
return Err(nb::Error::Other(e));
409+
}
410+
411+
if !sr.txe().bit_is_set() {
412+
Err(nb::Error::WouldBlock)
405413
} else {
406-
nb::Error::WouldBlock
407-
})
414+
Ok(())
415+
}
408416
}
409417

410418
fn read_u8(&mut self) -> u8 {
@@ -454,6 +462,32 @@ where
454462
}
455463
}
456464

465+
impl<SPI, SCKPIN, MISOPIN, MOSIPIN> ::embedded_hal::spi::FullDuplex<u8>
466+
for Spi<SPI, SCKPIN, MISOPIN, MOSIPIN, EightBit>
467+
where
468+
SPI: Deref<Target = SpiRegisterBlock>,
469+
{
470+
type Error = Error;
471+
472+
fn read(&mut self) -> nb::Result<u8, Error> {
473+
self.check_read()?;
474+
Ok(self.read_u8())
475+
}
476+
477+
fn send(&mut self, byte: u8) -> nb::Result<(), Error> {
478+
// We want to transfer bidirectionally, make sure we're in the correct mode
479+
self.set_bidi();
480+
481+
self.check_send()?;
482+
self.send_u8(byte);
483+
484+
match self.check_errors() {
485+
Ok(_) => Ok(()),
486+
Err(e) => Err(nb::Error::Other(e)),
487+
}
488+
}
489+
}
490+
457491
impl<SPI, SCKPIN, MISOPIN, MOSIPIN> ::embedded_hal::blocking::spi::Write<u8>
458492
for Spi<SPI, SCKPIN, MISOPIN, MOSIPIN, EightBit>
459493
where
@@ -482,8 +516,33 @@ where
482516
}
483517

484518
// Do one last status register check before continuing
485-
self.check_send().ok();
486-
Ok(())
519+
self.check_errors()
520+
}
521+
}
522+
523+
impl<SPI, SCKPIN, MISOPIN, MOSIPIN> ::embedded_hal::spi::FullDuplex<u16>
524+
for Spi<SPI, SCKPIN, MISOPIN, MOSIPIN, SixteenBit>
525+
where
526+
SPI: Deref<Target = SpiRegisterBlock>,
527+
{
528+
type Error = Error;
529+
530+
fn read(&mut self) -> nb::Result<u16, Error> {
531+
self.check_read()?;
532+
Ok(self.read_u16())
533+
}
534+
535+
fn send(&mut self, byte: u16) -> nb::Result<(), Error> {
536+
// We want to transfer bidirectionally, make sure we're in the correct mode
537+
self.set_bidi();
538+
539+
self.check_send()?;
540+
self.send_u16(byte);
541+
542+
match self.check_errors() {
543+
Ok(_) => Ok(()),
544+
Err(e) => Err(nb::Error::Other(e)),
545+
}
487546
}
488547
}
489548

@@ -526,7 +585,6 @@ where
526585
}
527586

528587
// Do one last status register check before continuing
529-
self.check_send().ok();
530-
Ok(())
588+
self.check_errors()
531589
}
532590
}

0 commit comments

Comments
 (0)