use simple_parse::{SpRead, SpWrite};
#[derive(SpRead, SpWrite, Debug)]
pub enum Message {
#[sp(id = "1")]
ServerHello(u32, u32),
#[sp(id = "2")]
ClientLogin,
#[sp(id = "3")]
ServerDisconnect {
#[sp(endian = "big")]
timestamp: u32,
_noptions: u8,
#[sp(count = "_noptions")]
options: Vec<u8>,
},
}
pub fn main() -> Result<(), Box<dyn std::error::Error>> {
let orig_buf: &[u8] = &[
0x01, 0x12, 0x23, 0x34, 0x45, 0x12, 0x34, 0x56, 0x78, 0x03, 0xDE, 0xAD, 0xBE, 0xEF, 0x2, 0x11, 0x22, ];
let mut start_idx = 0;
let mut cursor = orig_buf;
let mut dst: Vec<u8> = Vec::new();
println!("Decoding : {:X?}", orig_buf);
let mut msg = Message::from_bytes(&mut cursor)?;
println!("Got : {:X?}", msg);
{
dst.clear();
msg.to_bytes(&mut dst)?;
assert_eq!(&orig_buf[start_idx..start_idx + dst.len()], dst);
start_idx += dst.len();
}
println!("Decoding : {:X?}", cursor);
msg = Message::from_bytes(&mut cursor)?;
println!("Got : {:X?}", msg);
{
dst.clear();
msg.to_bytes(&mut dst)?;
assert_eq!(&orig_buf[start_idx..start_idx + dst.len()], dst);
}
if let Message::ServerDisconnect { options, .. } = &mut msg {
options.push(0x12);
println!("Added option to last message : {:X?}", options);
} else {
panic!("Did not parse as ServerDisconnect !?");
}
dst.clear();
msg.to_bytes(&mut dst)?;
println!("Encoding : {:X?}", dst);
{
dst.clear();
msg.to_bytes(&mut dst)?;
assert_eq!(
&dst,
&[
0x03, 0xDE, 0xAD, 0xBE, 0xEF, 0x3, 0x11, 0x22, 0x12, ]
);
}
Ok(())
}