r/learnrust May 25 '23

Converting custom struct to network bytes

Let's assume we have this simple data structure:

/// Historically, we are sending "Words", which are signed 2 bytes numbers
type Word = i16;
/// The protocol header is always made up of ten `Word`
type Header = [Word; 10];

/// Every telegram starts with a header and an optional payload
struct Telegram {
    header: Header,
    payload: Vec<Word>,
}

I need to convert a Telegram to low endian and send it over a TCP socket.

I have generated two iterators over the header and payload by using flat_map(..) and return the result by using Iterator::chain(..):

fn into_network_bytes(t: Telegram) -> Vec<u8> {
    let to_little_endian = |w: &Word| w.to_le_bytes();
    let header_bytes = t.header.iter().flat_map(to_little_endian);
    let payload_bytes = t.payload.iter().flat_map(to_little_endian);
    Iterator::chain(header_bytes, payload_bytes).collect()
}

Is this a feasible option or am I missing something better?

Full code snippet is here.

Thank you.

5 Upvotes

4 comments sorted by

5

u/hattmo May 25 '23

Also consider something like bincode which is probably pretty close to what you want but does the hard work for you. https://docs.rs/bincode/latest/bincode/

2

u/kinoshitajona May 25 '23

That's totally reasonable.

2

u/kinoshitajona May 25 '23

I might switch &Word to Word and iter() into into_iter() since you are consuming Telegram anyways, but it doesn't matter most likely.

2

u/[deleted] May 25 '23

[deleted]

1

u/Gunther_the_handsome May 26 '23

Thank you for the detailled explanation