device_driver/
buffer.rs

1use crate::{ReadCapability, WriteCapability};
2use core::marker::PhantomData;
3
4/// Common error definition for (async) [BufferInterface]
5pub trait BufferInterfaceError {
6    /// The error type
7    type Error;
8}
9
10/// A trait to represent the interface to the device.
11///
12/// This is called to read from and write to buffers.
13pub trait BufferInterface: BufferInterfaceError {
14    /// The address type used by this interface. Should likely be an integer.
15    type AddressType: Copy;
16
17    /// Write to the buffer with the given address.
18    ///
19    /// This interface must adhere to [embedded_io::Write::write].
20    fn write(&mut self, address: Self::AddressType, buf: &[u8]) -> Result<usize, Self::Error>;
21    /// Flush this output stream with the given address.
22    ///
23    /// This interface must adhere to [embedded_io::Write::flush].
24    fn flush(&mut self, address: Self::AddressType) -> Result<(), Self::Error>;
25    /// Read from the buffer with the given address.
26    ///
27    /// This interface must adhere to [embedded_io::Read::read].
28    fn read(&mut self, address: Self::AddressType, buf: &mut [u8]) -> Result<usize, Self::Error>;
29}
30
31/// A trait to represent the interface to the device.
32///
33/// This is called to read from and write to buffers.
34pub trait AsyncBufferInterface: BufferInterfaceError {
35    /// The address type used by this interface. Should likely be an integer.
36    type AddressType: Copy;
37
38    /// Write to the buffer with the given address.
39    ///
40    /// This interface must adhere to [embedded_io_async::Write::write].
41    async fn write(&mut self, address: Self::AddressType, buf: &[u8])
42    -> Result<usize, Self::Error>;
43    /// Flush this output stream with the given address.
44    ///
45    /// This interface must adhere to [embedded_io_async::Write::flush].
46    async fn flush(&mut self, address: Self::AddressType) -> Result<(), Self::Error>;
47    /// Read from the buffer with the given address.
48    ///
49    /// This interface must adhere to [embedded_io_async::Read::read].
50    async fn read(
51        &mut self,
52        address: Self::AddressType,
53        buf: &mut [u8],
54    ) -> Result<usize, Self::Error>;
55}
56
57/// Intermediate type for doing buffer operations
58///
59/// If the interface error implements [embedded_io::Error],
60/// then this operation type also implements the [embedded_io] traits
61pub struct BufferOperation<'i, Interface, AddressType: Copy, Access> {
62    interface: &'i mut Interface,
63    address: AddressType,
64    _phantom: PhantomData<Access>,
65}
66
67impl<'i, Interface, AddressType: Copy, Access> BufferOperation<'i, Interface, AddressType, Access> {
68    #[doc(hidden)]
69    pub fn new(interface: &'i mut Interface, address: AddressType) -> Self {
70        Self {
71            interface,
72            address,
73            _phantom: PhantomData,
74        }
75    }
76}
77
78impl<Interface, AddressType: Copy, Access> BufferOperation<'_, Interface, AddressType, Access>
79where
80    Interface: BufferInterface<AddressType = AddressType>,
81    Access: WriteCapability,
82{
83    /// Write a buffer into this writer, returning how many bytes were written.
84    ///
85    /// Mirror function of [embedded_io::Write::write].
86    pub fn write(&mut self, buf: &[u8]) -> Result<usize, Interface::Error> {
87        self.interface.write(self.address, buf)
88    }
89
90    /// Write an entire buffer into this writer.
91    ///
92    /// This function calls write() in a loop until exactly buf.len() bytes have been written, blocking if needed.
93    ///
94    /// Mirror function of [embedded_io::Write::write_all].
95    pub fn write_all(&mut self, mut buf: &[u8]) -> Result<(), Interface::Error> {
96        while !buf.is_empty() {
97            match self.write(buf) {
98                Ok(0) => panic!("write() returned Ok(0)"),
99                Ok(n) => buf = &buf[n..],
100                Err(e) => return Err(e),
101            }
102        }
103        Ok(())
104    }
105
106    /// Flush this output stream, blocking until all intermediately buffered contents reach their destination.
107    ///
108    /// Mirror function of [embedded_io::Write::flush].
109    pub fn flush(&mut self) -> Result<(), Interface::Error> {
110        self.interface.flush(self.address)
111    }
112}
113
114impl<Interface, AddressType: Copy, Access> BufferOperation<'_, Interface, AddressType, Access>
115where
116    Interface: BufferInterface<AddressType = AddressType>,
117    Access: ReadCapability,
118{
119    /// Read some bytes from this source into the specified buffer, returning how many bytes were read.
120    ///
121    /// Mirror function of [embedded_io::Read::read].
122    pub fn read(&mut self, buf: &mut [u8]) -> Result<usize, Interface::Error> {
123        self.interface.read(self.address, buf)
124    }
125
126    /// Read the exact number of bytes required to fill buf.
127    /// This function calls read() in a loop until exactly buf.len() bytes have been read, blocking if needed.
128    ///
129    /// Mirror function of [embedded_io::Read::read_exact].
130    pub fn read_exact(
131        &mut self,
132        mut buf: &mut [u8],
133    ) -> Result<(), embedded_io::ReadExactError<Interface::Error>> {
134        while !buf.is_empty() {
135            match self.read(buf) {
136                Ok(0) => break,
137                Ok(n) => buf = &mut buf[n..],
138                Err(e) => return Err(embedded_io::ReadExactError::Other(e)),
139            }
140        }
141        if buf.is_empty() {
142            Ok(())
143        } else {
144            Err(embedded_io::ReadExactError::UnexpectedEof)
145        }
146    }
147}
148
149impl<Interface, AddressType: Copy, Access> BufferOperation<'_, Interface, AddressType, Access>
150where
151    Interface: AsyncBufferInterface<AddressType = AddressType>,
152    Access: WriteCapability,
153{
154    /// Write a buffer into this writer, returning how many bytes were written.
155    ///
156    /// Mirror function of [embedded_io_async::Write::write].
157    pub async fn write_async(&mut self, buf: &[u8]) -> Result<usize, Interface::Error> {
158        self.interface.write(self.address, buf).await
159    }
160
161    /// Write an entire buffer into this writer.
162    ///
163    /// This function calls write() in a loop until exactly buf.len() bytes have been written, blocking if needed.
164    ///
165    /// Mirror function of [embedded_io_async::Write::write_all].
166    pub async fn write_all_async(&mut self, mut buf: &[u8]) -> Result<(), Interface::Error> {
167        while !buf.is_empty() {
168            match self.write_async(buf).await {
169                Ok(0) => panic!("write() returned Ok(0)"),
170                Ok(n) => buf = &buf[n..],
171                Err(e) => return Err(e),
172            }
173        }
174        Ok(())
175    }
176
177    /// Flush this output stream, blocking until all intermediately buffered contents reach their destination.
178    ///
179    /// Mirror function of [embedded_io_async::Write::flush].
180    pub async fn flush_async(&mut self) -> Result<(), Interface::Error> {
181        self.interface.flush(self.address).await
182    }
183}
184
185impl<Interface, AddressType: Copy, Access> BufferOperation<'_, Interface, AddressType, Access>
186where
187    Interface: AsyncBufferInterface<AddressType = AddressType>,
188    Access: ReadCapability,
189{
190    /// Read some bytes from this source into the specified buffer, returning how many bytes were read.
191    ///
192    /// Mirror function of [embedded_io_async::Read::read].
193    pub async fn read_async(&mut self, buf: &mut [u8]) -> Result<usize, Interface::Error> {
194        self.interface.read(self.address, buf).await
195    }
196
197    /// Read the exact number of bytes required to fill buf.
198    ///
199    /// This function calls read() in a loop until exactly buf.len() bytes have been read, waiting if needed.
200    ///
201    /// Mirror function of [embedded_io_async::Read::read_exact].
202    pub async fn read_exact_async(
203        &mut self,
204        mut buf: &mut [u8],
205    ) -> Result<(), embedded_io::ReadExactError<Interface::Error>> {
206        while !buf.is_empty() {
207            match self.read_async(buf).await {
208                Ok(0) => break,
209                Ok(n) => buf = &mut buf[n..],
210                Err(e) => return Err(embedded_io::ReadExactError::Other(e)),
211            }
212        }
213        if buf.is_empty() {
214            Ok(())
215        } else {
216            Err(embedded_io::ReadExactError::UnexpectedEof)
217        }
218    }
219}
220
221// ------- embedded-io impls -------
222
223impl<Interface, AddressType: Copy, Access> embedded_io::ErrorType
224    for BufferOperation<'_, Interface, AddressType, Access>
225where
226    Interface: BufferInterfaceError,
227    Interface::Error: embedded_io::Error,
228{
229    type Error = Interface::Error;
230}
231
232impl<Interface, AddressType: Copy, Access> embedded_io::Write
233    for BufferOperation<'_, Interface, AddressType, Access>
234where
235    Interface: BufferInterface<AddressType = AddressType>,
236    Interface::Error: embedded_io::Error,
237    Access: WriteCapability,
238{
239    fn write(&mut self, buf: &[u8]) -> Result<usize, Self::Error> {
240        self.write(buf)
241    }
242
243    fn flush(&mut self) -> Result<(), Self::Error> {
244        self.flush()
245    }
246}
247
248impl<Interface, AddressType: Copy, Access> embedded_io::Read
249    for BufferOperation<'_, Interface, AddressType, Access>
250where
251    Interface: BufferInterface<AddressType = AddressType>,
252    Interface::Error: embedded_io::Error,
253    Access: ReadCapability,
254{
255    fn read(&mut self, buf: &mut [u8]) -> Result<usize, Self::Error> {
256        self.read(buf)
257    }
258}
259
260impl<Interface, AddressType: Copy, Access> embedded_io_async::Write
261    for BufferOperation<'_, Interface, AddressType, Access>
262where
263    Interface: AsyncBufferInterface<AddressType = AddressType>,
264    Interface::Error: embedded_io::Error,
265    Access: WriteCapability,
266{
267    async fn write(&mut self, buf: &[u8]) -> Result<usize, Self::Error> {
268        self.write_async(buf).await
269    }
270
271    async fn flush(&mut self) -> Result<(), Self::Error> {
272        self.flush_async().await
273    }
274}
275
276impl<Interface, AddressType: Copy, Access> embedded_io_async::Read
277    for BufferOperation<'_, Interface, AddressType, Access>
278where
279    Interface: AsyncBufferInterface<AddressType = AddressType>,
280    Interface::Error: embedded_io::Error,
281    Access: ReadCapability,
282{
283    async fn read(&mut self, buf: &mut [u8]) -> Result<usize, Self::Error> {
284        self.read_async(buf).await
285    }
286}