1use crate::error::{JustcodeError, Result};
4use crate::reader::Reader;
5use crate::writer::Writer;
6
7pub fn encode_varint(writer: &mut Writer, mut value: u64) -> Result<()> {
17 loop {
18 let byte = (value & 0x7F) as u8;
19 value >>= 7;
20 if value == 0 {
21 writer.write_u8(byte)?;
22 break;
23 } else {
24 writer.write_u8(byte | 0x80)?;
25 }
26 }
27 Ok(())
28}
29
30pub fn decode_varint(reader: &mut Reader) -> Result<u64> {
32 let mut result = 0u64;
33 let mut shift = 0;
34
35 loop {
36 let byte = reader.read_u8()?;
37 result |= ((byte & 0x7F) as u64) << shift;
38
39 if (byte & 0x80) == 0 {
40 break;
41 }
42
43 shift += 7;
44 if shift >= 64 {
45 return Err(JustcodeError::InvalidVarint);
46 }
47 }
48
49 Ok(result)
50}
51
52pub fn encode_length(writer: &mut Writer, value: usize, config: crate::Config) -> Result<()> {
54 if config.variable_int_encoding {
55 encode_varint(writer, value as u64)
56 } else {
57 writer.write_u64(value as u64)
59 }
60}
61
62pub fn decode_length(reader: &mut Reader, config: crate::Config) -> Result<usize> {
64 if config.variable_int_encoding {
65 let value = decode_varint(reader)?;
66 Ok(value as usize)
67 } else {
68 let value = reader.read_u64()?;
70 Ok(value as usize)
71 }
72}
73
74#[cfg(test)]
75mod tests {
76 use super::*;
77 use crate::config;
78
79 #[test]
80 fn test_varint_encode_decode() {
81 let config = config::standard();
82 let test_cases = vec![
83 0u64,
84 1,
85 127,
86 128,
87 255,
88 256,
89 16383,
90 16384,
91 65535,
92 1000000,
93 u64::MAX,
94 ];
95
96 for value in test_cases {
97 let mut writer = Writer::new(config);
98 encode_varint(&mut writer, value).unwrap();
99 let bytes = writer.into_bytes();
100
101 let mut reader = Reader::new(&bytes, config);
102 let decoded = decode_varint(&mut reader).unwrap();
103 assert_eq!(value, decoded);
104 }
105 }
106
107 #[test]
108 fn test_length_encode_decode() {
109 let config = config::standard();
110 let test_cases = vec![0usize, 1, 127, 128, 255, 1000, 1000000];
111
112 for value in test_cases {
113 let mut writer = Writer::new(config);
114 encode_length(&mut writer, value, config).unwrap();
115 let bytes = writer.into_bytes();
116
117 let mut reader = Reader::new(&bytes, config);
118 let decoded = decode_length(&mut reader, config).unwrap();
119 assert_eq!(value, decoded);
120 }
121 }
122
123 #[test]
124 fn test_varint_small_values() {
125 let config = config::standard();
126 let value = 42u64;
127 let mut writer = Writer::new(config);
128 encode_varint(&mut writer, value).unwrap();
129 let bytes = writer.into_bytes();
130 assert_eq!(bytes.len(), 1);
132 }
133
134 #[test]
135 fn test_varint_multi_byte() {
136 let config = config::standard();
137 let value = 200u64;
139 let mut writer = Writer::new(config);
140 encode_varint(&mut writer, value).unwrap();
141 let bytes = writer.into_bytes();
142 assert_eq!(bytes.len(), 2);
143
144 let mut reader = Reader::new(&bytes, config);
145 let decoded = decode_varint(&mut reader).unwrap();
146 assert_eq!(value, decoded);
147 }
148
149 #[test]
150 fn test_varint_large_values() {
151 let config = config::standard();
152 let test_cases = vec![
154 (16384u64, 3), (2097151u64, 3), (268435455u64, 4), ];
158
159 for (value, expected_bytes) in test_cases {
160 let mut writer = Writer::new(config);
161 encode_varint(&mut writer, value).unwrap();
162 let bytes = writer.into_bytes();
163 assert_eq!(bytes.len(), expected_bytes, "Value {} should use {} bytes", value, expected_bytes);
164
165 let mut reader = Reader::new(&bytes, config);
166 let decoded = decode_varint(&mut reader).unwrap();
167 assert_eq!(value, decoded);
168 }
169 }
170
171 #[test]
172 fn test_invalid_varint() {
173 let config = config::standard();
174 let invalid_data = vec![0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80]; let mut reader = Reader::new(&invalid_data, config);
177 assert!(decode_varint(&mut reader).is_err());
178 }
179
180 #[test]
181 fn test_length_fixed_encoding() {
182 let config = config::standard().with_variable_int_encoding(false);
183 let value = 42usize;
184 let mut writer = Writer::new(config);
185 encode_length(&mut writer, value, config).unwrap();
186 let bytes = writer.into_bytes();
187 assert_eq!(bytes.len(), 8);
189
190 let mut reader = Reader::new(&bytes, config);
191 let decoded = decode_length(&mut reader, config).unwrap();
192 assert_eq!(value, decoded);
193 }
194
195 #[test]
196 fn test_length_varint_encoding() {
197 let config = config::standard().with_variable_int_encoding(true);
198 let value = 42usize;
199 let mut writer = Writer::new(config);
200 encode_length(&mut writer, value, config).unwrap();
201 let bytes = writer.into_bytes();
202 assert_eq!(bytes.len(), 1);
204
205 let mut reader = Reader::new(&bytes, config);
206 let decoded = decode_length(&mut reader, config).unwrap();
207 assert_eq!(value, decoded);
208 }
209
210 #[test]
211 fn test_length_large_value() {
212 let config = config::standard();
213 let value = 1000000usize;
214 let mut writer = Writer::new(config);
215 encode_length(&mut writer, value, config).unwrap();
216 let bytes = writer.into_bytes();
217
218 let mut reader = Reader::new(&bytes, config);
219 let decoded = decode_length(&mut reader, config).unwrap();
220 assert_eq!(value, decoded);
221 }
222}
223