bt_hci/param/
primitives.rs

1use crate::{ByteAlignedValue, FixedSizeValue, FromHciBytes, FromHciBytesError, WriteHci};
2
3unsafe impl FixedSizeValue for () {
4    #[inline(always)]
5    fn is_valid(_data: &[u8]) -> bool {
6        true
7    }
8}
9
10unsafe impl ByteAlignedValue for () {}
11
12impl<'de> FromHciBytes<'de> for &'static () {
13    #[inline(always)]
14    fn from_hci_bytes(data: &'de [u8]) -> Result<(Self, &'de [u8]), crate::FromHciBytesError> {
15        Ok((&(), data))
16    }
17}
18
19unsafe impl FixedSizeValue for bool {
20    #[inline(always)]
21    fn is_valid(data: &[u8]) -> bool {
22        !data.is_empty() && data[0] < 2
23    }
24}
25
26unsafe impl ByteAlignedValue for bool {}
27
28impl<'de> FromHciBytes<'de> for &'de bool {
29    #[inline(always)]
30    fn from_hci_bytes(data: &'de [u8]) -> Result<(Self, &'de [u8]), crate::FromHciBytesError> {
31        <bool as crate::ByteAlignedValue>::ref_from_hci_bytes(data)
32    }
33}
34
35impl WriteHci for &[u8] {
36    #[inline(always)]
37    fn size(&self) -> usize {
38        // Slice length is incremented to account for the prepended length byte
39        self.len() + 1
40    }
41
42    #[inline(always)]
43    fn write_hci<W: embedded_io::Write>(&self, mut writer: W) -> Result<(), W::Error> {
44        writer.write_all(&[self.len() as u8])?;
45        writer.write_all(self)
46    }
47
48    #[inline(always)]
49    async fn write_hci_async<W: embedded_io_async::Write>(&self, mut writer: W) -> Result<(), W::Error> {
50        writer.write_all(&[self.size() as u8]).await?;
51        writer.write_all(self).await
52    }
53}
54
55unsafe impl<T: FixedSizeValue, const N: usize> FixedSizeValue for [T; N] {
56    #[inline(always)]
57    fn is_valid(_data: &[u8]) -> bool {
58        true
59    }
60}
61
62unsafe impl<T: ByteAlignedValue, const N: usize> ByteAlignedValue for [T; N] {}
63
64impl<'de, T: ByteAlignedValue, const N: usize> FromHciBytes<'de> for &'de [T; N] {
65    #[inline(always)]
66    fn from_hci_bytes(data: &'de [u8]) -> Result<(Self, &'de [u8]), crate::FromHciBytesError> {
67        <[T; N] as crate::ByteAlignedValue>::ref_from_hci_bytes(data)
68    }
69}
70
71impl<T: WriteHci> WriteHci for Option<T> {
72    #[inline(always)]
73    fn size(&self) -> usize {
74        self.as_ref().map(|x| x.size()).unwrap_or_default()
75    }
76
77    #[inline(always)]
78    fn write_hci<W: embedded_io::Write>(&self, writer: W) -> Result<(), W::Error> {
79        match self {
80            Some(val) => val.write_hci(writer),
81            None => Ok(()),
82        }
83    }
84
85    #[inline(always)]
86    async fn write_hci_async<W: embedded_io_async::Write>(&self, writer: W) -> Result<(), W::Error> {
87        match self {
88            Some(val) => val.write_hci_async(writer).await,
89            None => Ok(()),
90        }
91    }
92}
93
94impl<'de, T: FromHciBytes<'de>> FromHciBytes<'de> for Option<T> {
95    fn from_hci_bytes(data: &'de [u8]) -> Result<(Self, &'de [u8]), FromHciBytesError> {
96        if data.is_empty() {
97            Ok((None, data))
98        } else {
99            T::from_hci_bytes(data).map(|(x, y)| (Some(x), y))
100        }
101    }
102}