1use core::future::Future;
4
5use embassy_sync::blocking_mutex::raw::RawMutex;
6use embassy_sync::mutex::Mutex;
7use embedded_io::{ErrorType, ReadExactError};
8
9use crate::controller::blocking::TryError;
10use crate::{ControllerToHostPacket, FromHciBytesError, HostToControllerPacket, ReadHci, ReadHciError, WriteHci};
11
12pub trait Transport: embedded_io::ErrorType {
14 fn read<'a>(&self, rx: &'a mut [u8]) -> impl Future<Output = Result<ControllerToHostPacket<'a>, Self::Error>>;
16 fn write<T: HostToControllerPacket>(&self, val: &T) -> impl Future<Output = Result<(), Self::Error>>;
18}
19
20pub struct SerialTransport<M: RawMutex, R, W> {
22 reader: Mutex<M, R>,
23 writer: Mutex<M, W>,
24}
25
26#[derive(Debug, Clone, Copy, PartialEq, Eq)]
28#[cfg_attr(feature = "defmt", derive(defmt::Format))]
29pub enum Error<E: embedded_io::Error> {
30 Read(ReadHciError<E>),
32 Write(E),
34}
35
36impl<E: embedded_io::Error> core::fmt::Display for Error<E> {
37 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
38 write!(f, "{:?}", self)
39 }
40}
41
42impl<E: embedded_io::Error> core::error::Error for Error<E> {}
43
44impl<E: embedded_io::Error> embedded_io::Error for Error<E> {
45 fn kind(&self) -> embedded_io::ErrorKind {
46 match self {
47 Self::Read(e) => e.kind(),
48 Self::Write(e) => e.kind(),
49 }
50 }
51}
52
53impl<E: embedded_io::Error> From<E> for Error<E> {
54 fn from(e: E) -> Self {
55 Self::Write(e)
56 }
57}
58
59impl<E: embedded_io::Error> From<ReadHciError<E>> for Error<E> {
60 fn from(e: ReadHciError<E>) -> Self {
61 Self::Read(e)
62 }
63}
64
65impl<E: embedded_io::Error> From<ReadExactError<E>> for Error<E> {
66 fn from(e: ReadExactError<E>) -> Self {
67 Self::Read(e.into())
68 }
69}
70
71impl<E: embedded_io::Error> From<FromHciBytesError> for Error<E> {
72 fn from(e: FromHciBytesError) -> Self {
73 Self::Read(e.into())
74 }
75}
76
77impl<M: RawMutex, R: embedded_io_async::Read, W: embedded_io_async::Write> SerialTransport<M, R, W> {
78 pub fn new(reader: R, writer: W) -> Self {
80 Self {
81 reader: Mutex::new(reader),
82 writer: Mutex::new(writer),
83 }
84 }
85}
86
87impl<
88 M: RawMutex,
89 R: embedded_io::ErrorType<Error = E>,
90 W: embedded_io::ErrorType<Error = E>,
91 E: embedded_io::Error,
92 > ErrorType for SerialTransport<M, R, W>
93{
94 type Error = Error<E>;
95}
96
97impl<
98 M: RawMutex,
99 R: embedded_io_async::Read<Error = E>,
100 W: embedded_io_async::Write<Error = E>,
101 E: embedded_io::Error,
102 > Transport for SerialTransport<M, R, W>
103{
104 async fn read<'a>(&self, rx: &'a mut [u8]) -> Result<ControllerToHostPacket<'a>, Self::Error> {
105 let mut r = self.reader.lock().await;
106 ControllerToHostPacket::read_hci_async(&mut *r, rx)
107 .await
108 .map_err(Error::Read)
109 }
110
111 async fn write<T: HostToControllerPacket>(&self, tx: &T) -> Result<(), Self::Error> {
112 let mut w = self.writer.lock().await;
113 WithIndicator(tx)
114 .write_hci_async(&mut *w)
115 .await
116 .map_err(|e| Error::Write(e))
117 }
118}
119
120impl<M: RawMutex, R: embedded_io::Read<Error = E>, W: embedded_io::Write<Error = E>, E: embedded_io::Error>
121 blocking::Transport for SerialTransport<M, R, W>
122{
123 fn read<'a>(&self, rx: &'a mut [u8]) -> Result<ControllerToHostPacket<'a>, TryError<Self::Error>> {
124 let mut r = self.reader.try_lock().map_err(|_| TryError::Busy)?;
125 ControllerToHostPacket::read_hci(&mut *r, rx)
126 .map_err(Error::Read)
127 .map_err(TryError::Error)
128 }
129
130 fn write<T: HostToControllerPacket>(&self, tx: &T) -> Result<(), TryError<Self::Error>> {
131 let mut w = self.writer.try_lock().map_err(|_| TryError::Busy)?;
132 WithIndicator(tx)
133 .write_hci(&mut *w)
134 .map_err(|e| Error::Write(e))
135 .map_err(TryError::Error)
136 }
137}
138
139pub struct WithIndicator<'a, T: HostToControllerPacket>(&'a T);
144
145impl<'a, T: HostToControllerPacket> WithIndicator<'a, T> {
146 pub fn new(pkt: &'a T) -> Self {
148 Self(pkt)
149 }
150}
151
152impl<T: HostToControllerPacket> WriteHci for WithIndicator<'_, T> {
153 #[inline(always)]
154 fn size(&self) -> usize {
155 1 + self.0.size()
156 }
157
158 #[inline(always)]
159 fn write_hci<W: embedded_io::Write>(&self, mut writer: W) -> Result<(), W::Error> {
160 T::KIND.write_hci(&mut writer)?;
161 self.0.write_hci(writer)
162 }
163
164 #[inline(always)]
165 async fn write_hci_async<W: embedded_io_async::Write>(&self, mut writer: W) -> Result<(), W::Error> {
166 T::KIND.write_hci_async(&mut writer).await?;
167 self.0.write_hci_async(writer).await
168 }
169}
170
171pub mod blocking {
172 use super::*;
174 use crate::controller::blocking::TryError;
175
176 pub trait Transport: embedded_io::ErrorType {
178 fn read<'a>(&self, rx: &'a mut [u8]) -> Result<ControllerToHostPacket<'a>, TryError<Self::Error>>;
180 fn write<T: HostToControllerPacket>(&self, val: &T) -> Result<(), TryError<Self::Error>>;
182 }
183}