Skip to main content

commonware_codec/types/
bytes.rs

1//! Implementations of Codec for byte types.
2//!
3//! For portability and consistency between architectures,
4//! the length of the [Bytes] must fit within a [u32].
5
6use crate::{Buf, BufsMut, EncodeSize, Error, RangeCfg, Read, Write};
7use bytes::{BufMut, Bytes};
8
9impl Write for Bytes {
10    #[inline]
11    fn write(&self, buf: &mut impl BufMut) {
12        self.len().write(buf);
13        buf.put_slice(self);
14    }
15
16    #[inline]
17    fn write_bufs(&self, buf: &mut impl BufsMut) {
18        self.len().write(buf);
19        buf.push(self.clone());
20    }
21}
22
23impl EncodeSize for Bytes {
24    #[inline]
25    fn encode_size(&self) -> usize {
26        self.len().encode_size() + self.len()
27    }
28
29    #[inline]
30    fn encode_inline_size(&self) -> usize {
31        self.len().encode_size()
32    }
33}
34
35impl Read for Bytes {
36    type Cfg = RangeCfg<usize>;
37
38    #[inline]
39    fn read_cfg(buf: &mut impl Buf, range: &Self::Cfg) -> Result<Self, Error> {
40        let len = usize::read_cfg(buf, range)?;
41        buf.try_take_owned(len).map_err(|_| Error::EndOfBuffer)
42    }
43}
44
45#[cfg(test)]
46mod tests {
47    use super::*;
48    use crate::{Copying, Decode, Encode};
49    use bytes::Bytes;
50
51    #[test]
52    fn test_bytes() {
53        let values = [
54            Bytes::new(),
55            Bytes::from_static(&[1, 2, 3]),
56            Bytes::from(vec![0; 300]),
57        ];
58        for value in values {
59            let encoded = value.encode();
60            let len = value.len();
61
62            // Valid decoding
63            let decoded = Bytes::decode_cfg(encoded, &(len..=len).into()).unwrap();
64            assert_eq!(value, decoded);
65
66            // Failure for too long
67            assert!(matches!(
68                Bytes::decode_cfg(value.encode(), &(0..len).into()),
69                Err(Error::InvalidLength(_))
70            ));
71
72            // Failure for too short
73            assert!(matches!(
74                Bytes::decode_cfg(value.encode(), &(len + 1..).into()),
75                Err(Error::InvalidLength(_))
76            ));
77
78            // Failure for a payload shorter than its length prefix
79            let encoded = value.encode();
80            let truncated = encoded.slice(..encoded.len() - 1);
81            assert!(matches!(
82                Bytes::decode_cfg(truncated, &(len..=len).into()),
83                Err(Error::EndOfBuffer)
84            ));
85        }
86    }
87
88    #[test]
89    fn test_conformity() {
90        assert_eq!(Bytes::new().encode(), &[0x00][..]);
91        assert_eq!(
92            Bytes::from_static(b"hello").encode(),
93            &[0x05, b'h', b'e', b'l', b'l', b'o'][..]
94        );
95        let long_bytes = Bytes::from(vec![0xAA; 150]);
96        let mut expected = vec![0x96, 0x01]; // Varint for 150
97        expected.extend_from_slice(&[0xAA; 150]);
98        assert_eq!(long_bytes.encode(), expected.as_slice());
99    }
100
101    #[test]
102    fn test_view() {
103        let value: Vec<Bytes> = (0..64).map(|_| Bytes::from(vec![7u8; 17])).collect();
104        let source = value.encode();
105        let cfg = ((..).into(), (..).into());
106        let range = source.as_ptr_range();
107
108        // Decoding from the owned buffer hands out views of it
109        let decoded = Vec::<Bytes>::decode_cfg(source.clone(), &cfg).unwrap();
110        assert_eq!(decoded, value);
111        assert!(decoded.iter().all(|b| range.contains(&b.as_ptr())));
112
113        // Decoding from a slice of it copies every field
114        let copied = Vec::<Bytes>::decode_cfg(Copying(&source), &cfg).unwrap();
115        assert_eq!(copied, value);
116        assert!(copied.iter().all(|b| !range.contains(&b.as_ptr())));
117    }
118
119    #[cfg(feature = "arbitrary")]
120    mod conformance {
121        use super::*;
122        use crate::conformance::CodecConformance;
123        use arbitrary::Arbitrary;
124
125        /// Newtype wrapper to implement Arbitrary for [super::Bytes].
126        #[derive(Debug)]
127        struct Bytes(super::Bytes);
128
129        impl Write for Bytes {
130            fn write(&self, buf: &mut impl BufMut) {
131                self.0.write(buf);
132            }
133        }
134
135        impl EncodeSize for Bytes {
136            fn encode_size(&self) -> usize {
137                self.0.encode_size()
138            }
139        }
140
141        impl Read for Bytes {
142            type Cfg = RangeCfg<usize>;
143
144            fn read_cfg(buf: &mut impl Buf, cfg: &Self::Cfg) -> Result<Self, Error> {
145                Ok(Self(super::Bytes::read_cfg(buf, cfg)?))
146            }
147        }
148
149        impl Arbitrary<'_> for Bytes {
150            fn arbitrary(u: &mut arbitrary::Unstructured<'_>) -> arbitrary::Result<Self> {
151                let len = u.arbitrary::<u8>()?;
152                let bytes: Vec<u8> = u
153                    .arbitrary_iter()?
154                    .take(len as usize)
155                    .collect::<Result<Vec<_>, _>>()
156                    .unwrap();
157                Ok(Self(super::Bytes::from(bytes)))
158            }
159        }
160
161        commonware_conformance::conformance_tests! {
162            CodecConformance<Bytes>
163        }
164    }
165}