sdmmc_core/response/spi/
r5.rs

1use crate::response::sdio::r1::R1;
2use crate::result::{Error, Result};
3use crate::{lib_bitfield, response};
4
5lib_bitfield! {
6    /// Represents the response to the `IO_RW_DIRECT` command (`CMD52`) in SPI mode.
7    pub R5(u16): u8 {
8        raw_r1: 15, 8;
9        raw_data: 7, 0;
10    }
11}
12
13response! {
14    R5 {
15        response_mode: Spi,
16    }
17}
18
19impl R5 {
20    /// Represents the byte length of the [R5] response.
21    pub const LEN: usize = 2;
22    /// Represents the default value of the [R5] response.
23    pub const DEFAULT: u16 = 0;
24
25    /// Creates a new [R5].
26    pub const fn new() -> Self {
27        Self(Self::DEFAULT)
28    }
29
30    /// Gets the [R1] field of the [R5].
31    pub const fn r1(&self) -> Result<R1> {
32        R1::try_from_bits(self.raw_r1())
33    }
34
35    /// Sets the [R1] field of the [R5].
36    pub fn set_r1(&mut self, val: R1) {
37        self.set_raw_r1(val.bits() as u16);
38    }
39
40    /// Gets the read/write `data` field of the [R5].
41    pub const fn data(&self) -> u8 {
42        self.raw_data()
43    }
44
45    /// Sets the read/write `data` field of the [R5].
46    pub fn set_data(&mut self, val: u8) {
47        self.set_raw_data(val as u16);
48    }
49
50    /// Attempts to convert a [`u16`] into a [R5].
51    pub const fn try_from_bits(val: u16) -> Result<Self> {
52        Self::try_from_bytes(&val.to_be_bytes())
53    }
54
55    /// Gets the byte value of the [R5].
56    pub const fn bytes(&self) -> [u8; Self::LEN] {
57        self.0.to_be_bytes()
58    }
59
60    /// Attempts to convert a byte slice into a [R5].
61    pub const fn try_from_bytes(val: &[u8]) -> Result<Self> {
62        match val.len() {
63            len if len < Self::LEN => Err(Error::invalid_length(len, Self::LEN)),
64            _ if R1::try_from_bits(val[0]).is_err() => {
65                Err(Error::invalid_field_variant("r5::r1", val[0] as usize))
66            }
67            _ => Ok(Self(u16::from_be_bytes([val[0], val[1]]))),
68        }
69    }
70}
71
72impl Default for R5 {
73    fn default() -> Self {
74        Self::new()
75    }
76}
77
78impl TryFrom<u16> for R5 {
79    type Error = Error;
80
81    fn try_from(val: u16) -> Result<Self> {
82        Self::try_from_bits(val)
83    }
84}
85
86impl From<R5> for u16 {
87    fn from(val: R5) -> Self {
88        val.bits()
89    }
90}
91
92impl TryFrom<&[u8]> for R5 {
93    type Error = Error;
94
95    fn try_from(val: &[u8]) -> Result<Self> {
96        Self::try_from_bytes(val)
97    }
98}
99
100impl<const N: usize> TryFrom<[u8; N]> for R5 {
101    type Error = Error;
102
103    fn try_from(val: [u8; N]) -> Result<Self> {
104        Self::try_from_bytes(val.as_ref())
105    }
106}
107
108impl<const N: usize> TryFrom<&[u8; N]> for R5 {
109    type Error = Error;
110
111    fn try_from(val: &[u8; N]) -> Result<Self> {
112        Self::try_from_bytes(val.as_ref())
113    }
114}
115
116impl From<R5> for [u8; R5::LEN] {
117    fn from(val: R5) -> Self {
118        val.bytes()
119    }
120}
121
122#[cfg(test)]
123mod tests {
124    use super::*;
125    use crate::test_field;
126
127    #[test]
128    fn test_fields() {
129        let r5 = R5::new();
130
131        let r1 = r5.r1().unwrap();
132
133        assert!(!r1.idle());
134        assert!(!r1.illegal_command());
135        assert!(!r1.crc_error());
136        assert!(!r1.function_number_error());
137        assert!(!r1.parameter_error());
138
139        assert_eq!(r5.data(), 0);
140
141        (0..=u8::MAX).zip(0..=u8::MAX).for_each(|(r1, data)| {
142            let raw = [r1, data];
143            let raw_r5 = u16::from_be_bytes(raw);
144
145            match R5::try_from_bytes(raw.as_ref()) {
146                Ok(mut r5) => {
147                    assert_eq!(R5::try_from_bytes(raw.as_ref()), Ok(r5));
148                    assert_eq!(R5::try_from(raw), Ok(r5));
149
150                    let mut r1 = r5.r1().unwrap();
151
152                    test_field!(r1, idle: 0);
153                    test_field!(r1, illegal_command: 2);
154                    test_field!(r1, crc_error: 3);
155                    test_field!(r1, function_number_error: 4);
156                    test_field!(r1, parameter_error: 6);
157
158                    r5.set_r1(R1::new());
159                    assert_eq!(r5.r1(), Ok(R1::new()));
160
161                    r5.set_r1(r1);
162                    assert_eq!(r5.r1(), Ok(r1));
163
164                    assert_eq!(r5.data(), data);
165
166                    r5.set_data(0);
167                    assert_eq!(r5.data(), 0);
168
169                    r5.set_data(data);
170                    assert_eq!(r5.data(), data);
171                }
172                Err(_) => {
173                    assert_eq!(
174                        R5::try_from_bytes(raw.as_ref()),
175                        Err(Error::invalid_field_variant("r5::r1", r1 as usize))
176                    );
177                    assert_eq!(
178                        R5::try_from(raw),
179                        Err(Error::invalid_field_variant("r5::r1", r1 as usize))
180                    );
181                }
182            }
183        });
184    }
185}