Skip to content

Commit 68825fc

Browse files
committed
spi/blocking: group methods into read-only, write-only and read-write traits.
1 parent a0bd3dc commit 68825fc

File tree

1 file changed

+38
-72
lines changed

1 file changed

+38
-72
lines changed

src/spi/blocking.rs

Lines changed: 38 additions & 72 deletions
Original file line numberDiff line numberDiff line change
@@ -1,53 +1,19 @@
11
//! Blocking SPI API
22
3-
/// Blocking transfer with separate buffers
4-
pub trait Transfer<W = u8> {
5-
/// Error type
6-
type Error: crate::spi::Error;
7-
8-
/// Writes and reads simultaneously. `write` is written to the slave on MOSI and
9-
/// words received on MISO are stored in `read`.
10-
///
11-
/// It is allowed for `read` and `write` to have different lengths, even zero length.
12-
/// The transfer runs for `max(read.len(), write.len())` words. If `read` is shorter,
13-
/// incoming words after `read` has been filled will be discarded. If `write` is shorter,
14-
/// the value of words sent in MOSI after all `write` has been sent is implementation-defined,
15-
/// typically `0x00`, `0xFF`, or configurable.
16-
fn transfer(&mut self, read: &mut [W], write: &[W]) -> Result<(), Self::Error>;
17-
}
18-
19-
impl<T: Transfer<W>, W> Transfer<W> for &mut T {
20-
type Error = T::Error;
21-
22-
fn transfer(&mut self, read: &mut [W], write: &[W]) -> Result<(), Self::Error> {
23-
T::transfer(self, read, write)
24-
}
25-
}
26-
27-
/// Blocking transfer with single buffer (in-place)
28-
pub trait TransferInplace<W = u8> {
3+
/// Base SPI trait
4+
///
5+
/// This just defines the error type, to be used by the other SPI traits.
6+
pub trait Spi {
297
/// Error type
308
type Error: crate::spi::Error;
31-
32-
/// Writes and reads simultaneously. The contents of `words` are
33-
/// written to the slave, and the received words are stored into the same
34-
/// `words` buffer, overwriting it.
35-
fn transfer_inplace(&mut self, words: &mut [W]) -> Result<(), Self::Error>;
369
}
3710

38-
impl<T: TransferInplace<W>, W> TransferInplace<W> for &mut T {
11+
impl<T: Spi> Spi for &mut T {
3912
type Error = T::Error;
40-
41-
fn transfer_inplace(&mut self, words: &mut [W]) -> Result<(), Self::Error> {
42-
T::transfer_inplace(self, words)
43-
}
4413
}
4514

46-
/// Blocking read
47-
pub trait Read<W = u8> {
48-
/// Error type
49-
type Error: crate::spi::Error;
50-
15+
/// Blocking read-only SPI
16+
pub trait Read<W = u8>: Spi {
5117
/// Reads `words` from the slave.
5218
///
5319
/// The word value sent on MOSI during reading is implementation-defined,
@@ -56,43 +22,26 @@ pub trait Read<W = u8> {
5622
}
5723

5824
impl<T: Read<W>, W> Read<W> for &mut T {
59-
type Error = T::Error;
60-
6125
fn read(&mut self, words: &mut [W]) -> Result<(), Self::Error> {
6226
T::read(self, words)
6327
}
6428
}
6529

66-
/// Blocking write
67-
pub trait Write<W = u8> {
68-
/// Error type
69-
type Error: crate::spi::Error;
70-
30+
/// Blocking write-only SPI
31+
pub trait Write<W = u8>: Spi {
7132
/// Writes `words` to the slave, ignoring all the incoming words
7233
fn write(&mut self, words: &[W]) -> Result<(), Self::Error>;
73-
}
74-
75-
impl<T: Write<W>, W> Write<W> for &mut T {
76-
type Error = T::Error;
77-
78-
fn write(&mut self, words: &[W]) -> Result<(), Self::Error> {
79-
T::write(self, words)
80-
}
81-
}
82-
83-
/// Blocking write (iterator version)
84-
pub trait WriteIter<W = u8> {
85-
/// Error type
86-
type Error: crate::spi::Error;
8734

8835
/// Writes `words` to the slave, ignoring all the incoming words
8936
fn write_iter<WI>(&mut self, words: WI) -> Result<(), Self::Error>
9037
where
9138
WI: IntoIterator<Item = W>;
9239
}
9340

94-
impl<T: WriteIter<W>, W> WriteIter<W> for &mut T {
95-
type Error = T::Error;
41+
impl<T: Write<W>, W> Write<W> for &mut T {
42+
fn write(&mut self, words: &[W]) -> Result<(), Self::Error> {
43+
T::write(self, words)
44+
}
9645

9746
fn write_iter<WI>(&mut self, words: WI) -> Result<(), Self::Error>
9847
where
@@ -117,18 +66,35 @@ pub enum Operation<'a, W: 'static = u8> {
11766
TransferInplace(&'a mut [W]),
11867
}
11968

120-
/// Transactional trait allows multiple actions to be executed
121-
/// as part of a single SPI transaction
122-
pub trait Transactional<W: 'static = u8> {
123-
/// Associated error type
124-
type Error: crate::spi::Error;
69+
/// Blocking read-write SPI
70+
pub trait ReadWrite<W = u8>: Read<W> + Write<W> {
71+
/// Writes and reads simultaneously. `write` is written to the slave on MOSI and
72+
/// words received on MISO are stored in `read`.
73+
///
74+
/// It is allowed for `read` and `write` to have different lengths, even zero length.
75+
/// The transfer runs for `max(read.len(), write.len())` words. If `read` is shorter,
76+
/// incoming words after `read` has been filled will be discarded. If `write` is shorter,
77+
/// the value of words sent in MOSI after all `write` has been sent is implementation-defined,
78+
/// typically `0x00`, `0xFF`, or configurable.
79+
fn transfer(&mut self, read: &mut [W], write: &[W]) -> Result<(), Self::Error>;
12580

126-
/// Execute the provided transactions
81+
/// Writes and reads simultaneously. The contents of `words` are
82+
/// written to the slave, and the received words are stored into the same
83+
/// `words` buffer, overwriting it.
84+
fn transfer_inplace(&mut self, words: &mut [W]) -> Result<(), Self::Error>;
85+
86+
/// Execute multiple actions as part of a single SPI transaction
12787
fn exec<'a>(&mut self, operations: &mut [Operation<'a, W>]) -> Result<(), Self::Error>;
12888
}
12989

130-
impl<T: Transactional<W>, W: 'static> Transactional<W> for &mut T {
131-
type Error = T::Error;
90+
impl<T: ReadWrite<W>, W> ReadWrite<W> for &mut T {
91+
fn transfer(&mut self, read: &mut [W], write: &[W]) -> Result<(), Self::Error> {
92+
T::transfer(self, read, write)
93+
}
94+
95+
fn transfer_inplace(&mut self, words: &mut [W]) -> Result<(), Self::Error> {
96+
T::transfer_inplace(self, words)
97+
}
13298

13399
fn exec<'a>(&mut self, operations: &mut [Operation<'a, W>]) -> Result<(), Self::Error> {
134100
T::exec(self, operations)

0 commit comments

Comments
 (0)