use bitbuffer::{ BigEndian, BitRead, BitReadBuffer, BitReadStream, BitWrite, BitWriteStream, LittleEndian, }; use std::fmt::Debug; #[track_caller] fn roundtrip< T: BitRead<'static, BigEndian> + BitWrite + BitRead<'static, LittleEndian> + BitWrite + Debug + PartialEq, >( val: T, ) { { let mut data = Vec::new(); let size = { let mut stream = BitWriteStream::new(&mut data, LittleEndian); stream.write(&val).unwrap(); stream.bit_len() }; let mut read = BitReadStream::new(BitReadBuffer::new_owned(data, LittleEndian)); assert_eq!(val, read.read().unwrap()); assert_eq!(size, read.pos()); } { let mut data = Vec::new(); let size = { let mut stream = BitWriteStream::new(&mut data, BigEndian); stream.write(&val).unwrap(); stream.bit_len() }; let mut read = BitReadStream::new(BitReadBuffer::new_owned(data, BigEndian)); assert_eq!(val, read.read().unwrap()); assert_eq!(size, read.pos()); } } #[test] fn test_basic_struct() { #[derive(Debug, PartialEq, BitRead, BitWrite)] struct Foo { int: u32, float: f64, #[size = 2] smaller_int: u8, signed: i32, #[size = 3] smaller_signed: i32, dynamic_string: String, #[size = 3] fixed_string: String, } roundtrip(Foo { int: 1234, float: 10.2, smaller_int: 3, signed: -3, smaller_signed: -1, dynamic_string: "Foobar".to_string(), fixed_string: "asd".to_string(), }); } #[test] fn test_bare_enum() { #[derive(Debug, PartialEq, BitRead, BitWrite)] #[discriminant_bits = 4] enum Enum { A, B, C, D, } roundtrip(Enum::A); roundtrip(Enum::B); roundtrip(Enum::C); roundtrip(Enum::D); } #[test] fn test_field_enum() { #[derive(Debug, PartialEq, BitRead, BitWrite)] struct CompoundVariant(#[size = 15] u16, bool); #[derive(Debug, PartialEq, BitRead, BitWrite)] #[discriminant_bits = 4] enum Enum { A, B(String), C(f32), D(#[size = 15] i64), E(CompoundVariant), } roundtrip(Enum::A); roundtrip(Enum::B("foobar".into())); roundtrip(Enum::C(12.0)); roundtrip(Enum::D(-12345)); roundtrip(Enum::E(CompoundVariant(6789, true))); } #[test] fn test_array() { roundtrip([1, 2, 3, 4, 5]); roundtrip([String::from("asd"), String::from("foobar")]); } #[test] fn test_tuple() { roundtrip((1, false)); roundtrip((1, 10.12, String::from("asd"))); }