code_rs/
bits.rs

1//! Dibits, tribits, and hexbits.
2
3use std;
4
5/// Iterate over the 2-bit symbols of a byte source, MSB to LSB.
6pub type Dibits<T> = SubByteIter<DibitParams, T>;
7/// Iterates over the 3-bit symbols of a byte source, MSB to LSB. The source must be a
8/// multiple of 3 bytes.
9pub type Tribits<T> = SubByteIter<TribitParams, T>;
10/// Iterates over the 6-bit symbols of a byte source, MSB to LSB. The source must be a
11/// multiple of 3 bytes.
12pub type Hexbits<T> = SubByteIter<HexbitParams, T>;
13
14/// Groups dibits into full bytes. The source must be a multiple of 4 dibits.
15pub type DibitBytes<T> = SubByteIter<DibitByteParams, T>;
16/// Groups tribits into full bytes. The source must be a multiple of 8 tribits.
17pub type TribitBytes<T> = SubByteIter<TribitByteParams, T>;
18/// Groups hexbits into full bytes. The source must be a multiple of 6 hexbits.
19pub type HexbitBytes<T> = SubByteIter<HexbitByteParams, T>;
20
21pub trait IterParams {
22    /// Type to consume when buffering.
23    type Input;
24    /// Type to yield at each iteration.
25    type Output;
26
27    /// Number of bits to consume at each iteration.
28    fn bits() -> usize;
29
30    /// Number of input symbols to consume when buffering.
31    fn buffer() -> usize;
32
33    /// Amount to shift buffer after loading an input symbol.
34    fn shift() -> usize;
35
36    /// Amount to shift buffer after all buffering, so the bits are lined up at the MSB.
37    fn post_shift() -> usize {
38        32 - Self::shift() * Self::buffer()
39    }
40
41    /// Number of iterations before buffering.
42    fn iterations() -> usize {
43        Self::shift() * Self::buffer() / Self::bits()
44    }
45
46    /// Convert input symbol to a byte.
47    fn to_byte(input: Self::Input) -> u8;
48
49    /// Convert bits to output type.
50    fn to_output(bits: u8) -> Self::Output;
51
52    /// Verify the parameters are supported.
53    fn validate() {
54        // Maximum buffer size is currently 32 bits.
55        assert!(Self::buffer() * Self::shift() <= 32);
56    }
57}
58
59/// Two bits.
60#[derive(Copy, Clone, Default, Debug, PartialEq, Eq)]
61pub struct Dibit(u8);
62
63impl Dibit {
64    /// Construct a new `Dibit` with the two given bits in the LSB position.
65    pub fn new(bits: u8) -> Dibit {
66        assert!(bits >> 2 == 0);
67        Dibit(bits)
68    }
69
70    /// Get the wrapped dibit, which is guaranteed to have only 2 LSBs.
71    pub fn bits(&self) -> u8 {
72        self.0
73    }
74    /// Get the MSB.
75    pub fn hi(&self) -> u8 {
76        self.0 >> 1
77    }
78    /// Get the LSB.
79    pub fn lo(&self) -> u8 {
80        self.0 & 1
81    }
82}
83
84/// Parameters for `Dibits` iterator.
85pub struct DibitParams;
86
87impl IterParams for DibitParams {
88    type Input = u8;
89    type Output = Dibit;
90
91    fn bits() -> usize {
92        2
93    }
94    fn buffer() -> usize {
95        1
96    }
97    fn shift() -> usize {
98        8
99    }
100
101    fn to_byte(input: Self::Input) -> u8 {
102        input
103    }
104    fn to_output(bits: u8) -> Dibit {
105        Dibit::new(bits)
106    }
107}
108
109/// Three bits.
110#[derive(Copy, Clone, Default, Debug, PartialEq, Eq)]
111pub struct Tribit(u8);
112
113impl Tribit {
114    /// Construct a new `Tribit` with the three given bits in the LSB position.
115    pub fn new(bits: u8) -> Tribit {
116        assert!(bits >> 3 == 0);
117        Tribit(bits)
118    }
119
120    /// Get the wrapped tribit, which is guaranteed to have only 3 LSBs.
121    pub fn bits(&self) -> u8 {
122        self.0
123    }
124}
125
126/// Parameters for `Tribits` iterator.
127pub struct TribitParams;
128
129impl IterParams for TribitParams {
130    type Input = u8;
131    type Output = Tribit;
132
133    fn bits() -> usize {
134        3
135    }
136    fn buffer() -> usize {
137        3
138    }
139    fn shift() -> usize {
140        8
141    }
142
143    fn to_byte(input: Self::Input) -> u8 {
144        input
145    }
146    fn to_output(bits: u8) -> Tribit {
147        Tribit::new(bits)
148    }
149}
150
151/// Six bits.
152#[derive(Copy, Clone, Default, Debug, PartialEq, Eq)]
153pub struct Hexbit(u8);
154
155impl Hexbit {
156    /// Construct a new `Hexbit` with the 6 given bits in the LSB position.
157    pub fn new(bits: u8) -> Hexbit {
158        assert!(bits >> 6 == 0);
159        Hexbit(bits)
160    }
161
162    /// Get the wrapped hexbit, which is guaranteed to have only 6 LSBs.
163    pub fn bits(&self) -> u8 {
164        self.0
165    }
166}
167
168/// Parameters for `Hexbits` iterator.
169pub struct HexbitParams;
170
171impl IterParams for HexbitParams {
172    type Input = u8;
173    type Output = Hexbit;
174
175    fn bits() -> usize {
176        6
177    }
178    fn buffer() -> usize {
179        3
180    }
181    fn shift() -> usize {
182        8
183    }
184
185    fn to_byte(input: Self::Input) -> u8 {
186        input
187    }
188    fn to_output(bits: u8) -> Hexbit {
189        Hexbit::new(bits)
190    }
191}
192
193/// Parameters for `DibitBytes` iterator.
194pub struct DibitByteParams;
195
196impl IterParams for DibitByteParams {
197    type Input = Dibit;
198    type Output = u8;
199
200    fn bits() -> usize {
201        8
202    }
203    fn buffer() -> usize {
204        4
205    }
206    fn shift() -> usize {
207        2
208    }
209
210    fn to_byte(input: Self::Input) -> u8 {
211        input.bits()
212    }
213    fn to_output(bits: u8) -> Self::Output {
214        bits
215    }
216}
217
218/// Parameters for `TribitBytes` iterator.
219pub struct TribitByteParams;
220
221impl IterParams for TribitByteParams {
222    type Input = Tribit;
223    type Output = u8;
224
225    fn bits() -> usize {
226        8
227    }
228    fn buffer() -> usize {
229        8
230    }
231    fn shift() -> usize {
232        3
233    }
234
235    fn to_byte(input: Self::Input) -> u8 {
236        input.bits()
237    }
238    fn to_output(bits: u8) -> Self::Output {
239        bits
240    }
241}
242
243/// Parameters for `HexbitBytes` iterator.
244pub struct HexbitByteParams;
245
246impl IterParams for HexbitByteParams {
247    type Input = Hexbit;
248    type Output = u8;
249
250    fn bits() -> usize {
251        8
252    }
253    fn buffer() -> usize {
254        4
255    }
256    fn shift() -> usize {
257        6
258    }
259
260    fn to_byte(input: Self::Input) -> u8 {
261        input.bits()
262    }
263    fn to_output(bits: u8) -> Self::Output {
264        bits
265    }
266}
267
268/// An iterator for sub-byte (bit-level) values.
269pub struct SubByteIter<P, T>
270where
271    P: IterParams,
272    T: Iterator<Item = P::Input>,
273{
274    params: std::marker::PhantomData<P>,
275    /// Source of bytes.
276    src: T,
277    /// Current buffered bits.
278    buf: u32,
279    /// Current bit-level index into the current byte.
280    idx: u8,
281}
282
283impl<P, T> SubByteIter<P, T>
284where
285    P: IterParams,
286    T: Iterator<Item = P::Input>,
287{
288    /// Construct a new `SubByteIter` over the given symbol source.
289    pub fn new(src: T) -> SubByteIter<P, T> {
290        SubByteIter {
291            params: std::marker::PhantomData,
292            src,
293            buf: 0,
294            idx: 0,
295        }
296    }
297
298    /// Consume one or more symbols to create a buffer of bits, filled starting from the
299    /// MSB.
300    fn buffer(&mut self) -> Option<u32> {
301        let (buf, added) = (&mut self.src)
302            .take(P::buffer())
303            .fold((0, 0), |(buf, added), next| {
304                (buf << P::shift() | P::to_byte(next) as u32, added + 1)
305            });
306
307        // It's okay if there are no more source symbols here, because we're on a safe
308        // boundary.
309        if added == 0 {
310            return None;
311        }
312
313        assert!(added == P::buffer(), "incomplete source");
314
315        Some(buf << P::post_shift())
316    }
317}
318
319impl<P, T> Iterator for SubByteIter<P, T>
320where
321    P: IterParams,
322    T: Iterator<Item = P::Input>,
323{
324    type Item = P::Output;
325
326    fn next(&mut self) -> Option<Self::Item> {
327        if self.idx == 0 {
328            self.buf = match self.buffer() {
329                Some(b) => b,
330                None => return None,
331            };
332        }
333
334        // Extract MSBs.
335        let bits = self.buf >> (32 - P::bits());
336
337        // Strip off the MSBs for the next iteration.
338        self.buf <<= P::bits();
339
340        // Move to the next item and reset after all have been visited.
341        self.idx += 1;
342        self.idx %= P::iterations() as u8;
343
344        Some(P::to_output(bits as u8))
345    }
346}
347
348#[cfg(test)]
349mod test {
350    use super::*;
351
352    #[test]
353    fn validate_params() {
354        DibitParams::validate();
355        TribitParams::validate();
356        HexbitParams::validate();
357        DibitByteParams::validate();
358        TribitByteParams::validate();
359        HexbitByteParams::validate();
360    }
361
362    #[test]
363    fn test_dibits() {
364        let bytes = [0b00110011, 0b10011001, 0b11111111];
365
366        let mut d = Dibits::new(bytes.iter().cloned());
367
368        assert_eq!(d.next().unwrap().bits(), 0b00);
369        assert_eq!(d.next().unwrap().bits(), 0b11);
370        assert_eq!(d.next().unwrap().bits(), 0b00);
371        assert_eq!(d.next().unwrap().bits(), 0b11);
372        assert_eq!(d.next().unwrap().bits(), 0b10);
373        assert_eq!(d.next().unwrap().bits(), 0b01);
374        assert_eq!(d.next().unwrap().bits(), 0b10);
375        assert_eq!(d.next().unwrap().bits(), 0b01);
376        assert_eq!(d.next().unwrap().bits(), 0b11);
377        assert_eq!(d.next().unwrap().bits(), 0b11);
378        assert_eq!(d.next().unwrap().bits(), 0b11);
379        assert_eq!(d.next().unwrap().bits(), 0b11);
380        assert!(d.next().is_none());
381    }
382
383    #[test]
384    fn test_dibit_bytes() {
385        let dibits = [
386            Dibit::new(0b00),
387            Dibit::new(0b11),
388            Dibit::new(0b00),
389            Dibit::new(0b11),
390            Dibit::new(0b10),
391            Dibit::new(0b01),
392            Dibit::new(0b10),
393            Dibit::new(0b01),
394            Dibit::new(0b11),
395            Dibit::new(0b11),
396            Dibit::new(0b11),
397            Dibit::new(0b11),
398        ];
399
400        let mut d = DibitBytes::new(dibits.iter().cloned());
401
402        assert_eq!(d.next().unwrap(), 0b00110011);
403        assert_eq!(d.next().unwrap(), 0b10011001);
404        assert_eq!(d.next().unwrap(), 0b11111111);
405        assert!(d.next().is_none());
406    }
407
408    #[test]
409    #[should_panic]
410    fn test_dibit_bytes_panic() {
411        let dibits = [
412            Dibit::new(0b00),
413            Dibit::new(0b11),
414            Dibit::new(0b00),
415            Dibit::new(0b11),
416            Dibit::new(0b10),
417        ];
418
419        let mut d = DibitBytes::new(dibits.iter().cloned());
420
421        d.next();
422        d.next();
423    }
424
425    #[test]
426    fn test_tribits() {
427        let bytes = [
428            0b00101001, 0b11001011, 0b10111000, 0b00101001, 0b11001011, 0b10111000,
429        ];
430        let mut t = Tribits::new(bytes.iter().cloned());
431
432        assert_eq!(t.next().unwrap().bits(), 0b001);
433        assert_eq!(t.next().unwrap().bits(), 0b010);
434        assert_eq!(t.next().unwrap().bits(), 0b011);
435        assert_eq!(t.next().unwrap().bits(), 0b100);
436        assert_eq!(t.next().unwrap().bits(), 0b101);
437        assert_eq!(t.next().unwrap().bits(), 0b110);
438        assert_eq!(t.next().unwrap().bits(), 0b111);
439        assert_eq!(t.next().unwrap().bits(), 0b000);
440        assert_eq!(t.next().unwrap().bits(), 0b001);
441        assert_eq!(t.next().unwrap().bits(), 0b010);
442        assert_eq!(t.next().unwrap().bits(), 0b011);
443        assert_eq!(t.next().unwrap().bits(), 0b100);
444        assert_eq!(t.next().unwrap().bits(), 0b101);
445        assert_eq!(t.next().unwrap().bits(), 0b110);
446        assert_eq!(t.next().unwrap().bits(), 0b111);
447        assert_eq!(t.next().unwrap().bits(), 0b000);
448        assert!(t.next().is_none());
449    }
450
451    #[test]
452    #[should_panic]
453    fn test_tribits_panic() {
454        let bytes = [1, 2, 3, 4];
455        let t = Tribits::new(bytes.iter().cloned());
456
457        for _ in t {}
458    }
459
460    #[test]
461    fn test_tribit_bytes() {
462        let tribits = [
463            Tribit::new(0b001),
464            Tribit::new(0b010),
465            Tribit::new(0b011),
466            Tribit::new(0b100),
467            Tribit::new(0b101),
468            Tribit::new(0b110),
469            Tribit::new(0b111),
470            Tribit::new(0b000),
471            Tribit::new(0b001),
472            Tribit::new(0b010),
473            Tribit::new(0b011),
474            Tribit::new(0b100),
475            Tribit::new(0b101),
476            Tribit::new(0b110),
477            Tribit::new(0b111),
478            Tribit::new(0b000),
479        ];
480
481        let mut t = TribitBytes::new(tribits.iter().cloned());
482
483        assert_eq!(t.next().unwrap(), 0b00101001);
484        assert_eq!(t.next().unwrap(), 0b11001011);
485        assert_eq!(t.next().unwrap(), 0b10111000);
486        assert_eq!(t.next().unwrap(), 0b00101001);
487        assert_eq!(t.next().unwrap(), 0b11001011);
488        assert_eq!(t.next().unwrap(), 0b10111000);
489        assert!(t.next().is_none());
490    }
491
492    #[test]
493    #[should_panic]
494    fn test_tribit_bytes_panic() {
495        let tribits = [
496            Tribit::new(0b001),
497            Tribit::new(0b010),
498            Tribit::new(0b011),
499            Tribit::new(0b100),
500        ];
501
502        let mut t = TribitBytes::new(tribits.iter().cloned());
503
504        t.next();
505        t.next();
506    }
507
508    #[test]
509    fn test_hexbits() {
510        let bytes = [
511            0b11111100, 0b00001010, 0b10010101, 0b11111100, 0b00001010, 0b10010101,
512        ];
513
514        let mut h = Hexbits::new(bytes.iter().cloned());
515
516        assert_eq!(h.next().unwrap().bits(), 0b111111);
517        assert_eq!(h.next().unwrap().bits(), 0b000000);
518        assert_eq!(h.next().unwrap().bits(), 0b101010);
519        assert_eq!(h.next().unwrap().bits(), 0b010101);
520        assert_eq!(h.next().unwrap().bits(), 0b111111);
521        assert_eq!(h.next().unwrap().bits(), 0b000000);
522        assert_eq!(h.next().unwrap().bits(), 0b101010);
523        assert_eq!(h.next().unwrap().bits(), 0b010101);
524        assert!(h.next().is_none());
525    }
526
527    #[test]
528    #[should_panic]
529    fn test_hexbits_panic() {
530        let bytes = [0b11111100, 0b00001010];
531
532        let mut h = Hexbits::new(bytes.iter().cloned());
533
534        assert_eq!(h.next().unwrap().bits(), 0b111111);
535        assert_eq!(h.next().unwrap().bits(), 0b000000);
536        h.next();
537    }
538
539    #[test]
540    fn test_hexbit_bytes() {
541        let hexbits = [
542            Hexbit::new(0b111111),
543            Hexbit::new(0b000000),
544            Hexbit::new(0b101010),
545            Hexbit::new(0b010101),
546            Hexbit::new(0b111111),
547            Hexbit::new(0b000000),
548            Hexbit::new(0b101010),
549            Hexbit::new(0b010101),
550        ];
551
552        let mut h = HexbitBytes::new(hexbits.iter().cloned());
553
554        assert_eq!(h.next().unwrap(), 0b11111100);
555        assert_eq!(h.next().unwrap(), 0b00001010);
556        assert_eq!(h.next().unwrap(), 0b10010101);
557        assert_eq!(h.next().unwrap(), 0b11111100);
558        assert_eq!(h.next().unwrap(), 0b00001010);
559        assert_eq!(h.next().unwrap(), 0b10010101);
560        assert!(h.next().is_none());
561    }
562
563    #[test]
564    #[should_panic]
565    fn test_hexbit_bytes_panic() {
566        let hexbits = [
567            Hexbit::new(0b111111),
568            Hexbit::new(0b000000),
569            Hexbit::new(0b101010),
570            Hexbit::new(0b010101),
571            Hexbit::new(0b111111),
572        ];
573
574        let mut h = HexbitBytes::new(hexbits.iter().cloned());
575        h.next();
576        h.next();
577        h.next();
578        h.next();
579        h.next();
580        h.next();
581    }
582}