Skip to main content

blocky_net/
types.rs

1use std::{
2    io::{Read, Write},
3    ops::{Deref, DerefMut},
4};
5
6use crate::{decoder::Decoder, encoder::Encoder};
7
8static SEGMENT_BITS: u8 = 0b01111111;
9static CONTINUE_BIT: u8 = 0b10000000;
10
11#[derive(Debug, PartialEq, Eq, Hash, Clone, Default, PartialOrd, Ord)]
12pub struct VarInt(pub i32);
13
14impl From<i32> for VarInt {
15    fn from(value: i32) -> Self {
16        Self(value)
17    }
18}
19
20impl Deref for VarInt {
21    type Target = i32;
22
23    fn deref(&self) -> &Self::Target {
24        &self.0
25    }
26}
27
28impl DerefMut for VarInt {
29    fn deref_mut(&mut self) -> &mut Self::Target {
30        &mut self.0
31    }
32}
33
34impl Decoder for VarInt {
35    fn decode<T: Read>(buf: &mut T) -> anyhow::Result<Self> {
36        let mut value = 0;
37        let mut position = 0;
38        let mut byte_buf = [0];
39
40        loop {
41            // read a byte from the buffer
42            buf.read_exact(&mut byte_buf)?;
43
44            let byte = byte_buf[0];
45
46            value |= ((byte & SEGMENT_BITS) as i32) << position;
47
48            if byte & CONTINUE_BIT == 0 {
49                break;
50            }
51
52            position += 7;
53
54            if position >= 32 {
55                anyhow::bail!("VarInt is too big");
56            }
57        }
58
59        Ok(Self(value))
60    }
61}
62
63impl Encoder for VarInt {
64    fn byte_len(&self) -> usize {
65        for i in 1..5 {
66            if (self.0 & -1 << (i * 7)) != 0 {
67                continue;
68            }
69
70            return i;
71        }
72
73        5
74    }
75
76    fn encode<T: Write>(&self, buf: &mut T) -> anyhow::Result<()> {
77        let mut value = self.0;
78
79        loop {
80            if (value & !(SEGMENT_BITS as i32)) == 0 {
81                buf.write_all(&[value as u8])?;
82                break;
83            }
84
85            buf.write_all(&[((value & (SEGMENT_BITS as i32)) | (CONTINUE_BIT as i32)) as u8])?;
86            value = ((value as u32) >> 7) as i32;
87        }
88
89        Ok(())
90    }
91}
92
93#[derive(Debug, PartialEq, Eq, Hash, Clone, Default, PartialOrd, Ord)]
94pub struct VarLong(pub i64);
95
96impl From<i64> for VarLong {
97    fn from(value: i64) -> Self {
98        Self(value)
99    }
100}
101
102impl Deref for VarLong {
103    type Target = i64;
104
105    fn deref(&self) -> &Self::Target {
106        &self.0
107    }
108}
109
110impl DerefMut for VarLong {
111    fn deref_mut(&mut self) -> &mut Self::Target {
112        &mut self.0
113    }
114}
115
116impl Decoder for VarLong {
117    fn decode<T: Read>(buf: &mut T) -> anyhow::Result<Self> {
118        let mut value = 0;
119        let mut position = 0;
120        let mut byte_buf = [0];
121
122        loop {
123            // read a byte from the buffer
124            buf.read_exact(&mut byte_buf)?;
125
126            let byte = byte_buf[0];
127
128            value |= ((byte & SEGMENT_BITS) as i64) << position;
129
130            if byte & CONTINUE_BIT == 0 {
131                break;
132            }
133
134            position += 7;
135
136            if position >= 64 {
137                anyhow::bail!("VarLong is too big");
138            }
139        }
140
141        Ok(Self(value))
142    }
143}
144
145impl Encoder for VarLong {
146    fn byte_len(&self) -> usize {
147        for i in 1..10 {
148            if (self.0 & -1 << (i * 7)) != 0 {
149                continue;
150            }
151
152            return i;
153        }
154
155        10
156    }
157
158    fn encode<T: Write>(&self, buf: &mut T) -> anyhow::Result<()> {
159        let mut value = self.0;
160
161        loop {
162            if (value & !(SEGMENT_BITS as i64)) == 0 {
163                buf.write_all(&[value as u8])?;
164                break;
165            }
166
167            buf.write_all(&[((value & (SEGMENT_BITS as i64)) | (CONTINUE_BIT as i64)) as u8])?;
168            value = ((value as u64) >> 7) as i64;
169        }
170
171        Ok(())
172    }
173}
174
175#[cfg(test)]
176mod tests {
177    use super::*;
178    use std::io::Cursor;
179
180    #[test]
181    fn test_varint_decode_single_byte() {
182        let mut buf = Cursor::new(vec![0x01]);
183        let varint = VarInt::decode(&mut buf).unwrap();
184        assert_eq!(varint.0, 1);
185    }
186
187    #[test]
188    fn test_varint_decode_multi_byte() {
189        let mut buf = Cursor::new(vec![0x80, 0x01]);
190        let varint = VarInt::decode(&mut buf).unwrap();
191        assert_eq!(varint.0, 128);
192    }
193
194    #[test]
195    fn test_varint_decode_max_positive() {
196        let mut buf = Cursor::new(vec![0xFF, 0xFF, 0xFF, 0xFF, 0x07]);
197        let varint = VarInt::decode(&mut buf).unwrap();
198        assert_eq!(varint.0, 2147483647);
199    }
200
201    #[test]
202    fn test_varint_decode_negative_one() {
203        let mut buf = Cursor::new(vec![0xFF, 0xFF, 0xFF, 0xFF, 0x0F]);
204        let varint = VarInt::decode(&mut buf).unwrap();
205        assert_eq!(varint.0, -1);
206    }
207
208    #[test]
209    fn test_varint_decode_min_negative() {
210        let mut buf = Cursor::new(vec![0x80, 0x80, 0x80, 0x80, 0x08]);
211        let varint = VarInt::decode(&mut buf).unwrap();
212        assert_eq!(varint.0, -2147483648);
213    }
214
215    #[test]
216    fn test_varint_decode_too_large() {
217        let mut buf = Cursor::new(vec![0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01]);
218        assert!(VarInt::decode(&mut buf).is_err());
219    }
220
221    #[test]
222    fn test_varlong_decode_single_byte() {
223        let mut buf = Cursor::new(vec![0x01]);
224        let varlong = VarLong::decode(&mut buf).unwrap();
225        assert_eq!(varlong.0, 1);
226    }
227
228    #[test]
229    fn test_varlong_decode_multi_byte() {
230        let mut buf = Cursor::new(vec![0x80, 0x01]);
231        let varlong = VarLong::decode(&mut buf).unwrap();
232        assert_eq!(varlong.0, 128);
233    }
234
235    #[test]
236    fn test_varlong_decode_max_positive() {
237        let mut buf = Cursor::new(vec![0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F]);
238        let varlong = VarLong::decode(&mut buf).unwrap();
239        assert_eq!(varlong.0, 9223372036854775807);
240    }
241
242    #[test]
243    fn test_varlong_decode_negative_one() {
244        let mut buf = Cursor::new(vec![
245            0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01,
246        ]);
247        let varlong = VarLong::decode(&mut buf).unwrap();
248        assert_eq!(varlong.0, -1);
249    }
250
251    #[test]
252    fn test_varlong_decode_min_negative() {
253        let mut buf = Cursor::new(vec![
254            0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x01,
255        ]);
256        let varlong = VarLong::decode(&mut buf).unwrap();
257        assert_eq!(varlong.0, -9223372036854775808);
258    }
259
260    #[test]
261    fn test_varlong_decode_too_large() {
262        let mut buf = Cursor::new(vec![
263            0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01,
264        ]);
265        assert!(VarLong::decode(&mut buf).is_err());
266    }
267
268    #[test]
269    fn test_varint_encode_single_byte() {
270        let varint = VarInt(1);
271        let mut buf = Vec::new();
272        varint.encode(&mut buf).unwrap();
273        assert_eq!(buf, vec![0x01]);
274    }
275
276    #[test]
277    fn test_varint_encode_multi_byte() {
278        let varint = VarInt(128);
279        let mut buf = Vec::new();
280        varint.encode(&mut buf).unwrap();
281        assert_eq!(buf, vec![0x80, 0x01]);
282    }
283
284    #[test]
285    fn test_varint_encode_max_positive() {
286        let varint = VarInt(2147483647);
287        let mut buf = Vec::new();
288        varint.encode(&mut buf).unwrap();
289        assert_eq!(buf, vec![0xFF, 0xFF, 0xFF, 0xFF, 0x07]);
290    }
291
292    #[test]
293    fn test_varint_encode_negative_one() {
294        let varint = VarInt(-1);
295        let mut buf = Vec::new();
296        varint.encode(&mut buf).unwrap();
297        assert_eq!(buf, vec![0xFF, 0xFF, 0xFF, 0xFF, 0x0F]);
298    }
299
300    #[test]
301    fn test_varint_encode_min_negative() {
302        let varint = VarInt(-2147483648);
303        let mut buf = Vec::new();
304        varint.encode(&mut buf).unwrap();
305        assert_eq!(buf, vec![0x80, 0x80, 0x80, 0x80, 0x08]);
306    }
307
308    #[test]
309    fn test_varlong_encode_single_byte() {
310        let varlong = VarLong(1);
311        let mut buf = Vec::new();
312        varlong.encode(&mut buf).unwrap();
313        assert_eq!(buf, vec![0x01]);
314    }
315
316    #[test]
317    fn test_varlong_encode_multi_byte() {
318        let varlong = VarLong(128);
319        let mut buf = Vec::new();
320        varlong.encode(&mut buf).unwrap();
321        assert_eq!(buf, vec![0x80, 0x01]);
322    }
323
324    #[test]
325    fn test_varlong_encode_max_positive() {
326        let varlong = VarLong(9223372036854775807);
327        let mut buf = Vec::new();
328        varlong.encode(&mut buf).unwrap();
329        assert_eq!(
330            buf,
331            vec![0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F]
332        );
333    }
334
335    #[test]
336    fn test_varlong_encode_negative_one() {
337        let varlong = VarLong(-1);
338        let mut buf = Vec::new();
339        varlong.encode(&mut buf).unwrap();
340        assert_eq!(
341            buf,
342            vec![0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x01]
343        );
344    }
345
346    #[test]
347    fn test_varlong_encode_min_negative() {
348        let varlong = VarLong(-9223372036854775808);
349        let mut buf = Vec::new();
350        varlong.encode(&mut buf).unwrap();
351        assert_eq!(
352            buf,
353            vec![0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x01]
354        );
355    }
356}