Resend is a easy to use, performant, customizable and extendable Rust library for little-endian/big-endian serializing and deserializing.
Two functions only:
snd() for any Write implementors (File, TcpStream etc)
rcv() for any Read implementors (File, TcpStream etc)
Cargo.toml: ```toml [dependencies]
resend = {version = "0.1", features = ["little"]}
Code:
rust
use resend::{Snd, Rcv};
let mut vec = Vec::new(); vec.snd(-8i8)?; vec.snd(22u16)?; vec.snd(0xFFABCDEF as u32)?; vec.snd("Test")?;
let mut buf = &vec[..]; let v: i8 = buf.rcv()?; let v: u16 = buf.rcv()?; let v: u32 = buf.rcv()?; let v: String = buf.rcv()?; ```
toml
[dependencies]
resend = {version = "0.1", features = ["little"]}
resend_derive = "0.1"
```rust use resend::{Snd, Rcv, endian::{Ascii, UTF16}}; use resend_derive::{Snd, Rcv};
pub enum DeviceType { PrinterType(IoPrinter) = 4, ScardType = 0x20, }
struct Device{ deviceid: u32, #[len(8)] dosname: Ascii, }
pub struct IoPrinter{ device: Device, length: u32, flags: u32, codepage: u32, pnpnamelen: u32, drivernamelen: u32, #[len(pnpnamelen)] pnpname: UTF16, #[len(drivernamelen)] driver_name: UTF16, }
... let dt: DeviceType = stream.rcv()?; stream.snd(&dt)?;
```
Write/Read trait based, no intermediate variables.
```rust
enum Color { Red, Blue = 32, Green =4, }
``` Color::Red is serialized as 0u16. Color::Blue is serialized as 32u16.
```rust
pub enum DeviceType { PrinterType(IoPrinter) = 4, ScardType = 0x20, } ``` DeviceType::PrinterType(printer) is serialized as 4u32 + IoPrinter data. DeviceType::ScardType is serialized as 0x20u32.
Please be aware: discriminants on non-unit variants are experimental for now (Rust 1.65), you have to use Rust nightly for this.
rust
stream.snd(BE(100_u32))?;
No serialization with #[skip] attribute.
The length of String, Vector etc. can be from another field or constant with #[len(fieldnameor_const)] attribute: ```rust
``` 4. #[when(expr)] attribute is used on Option field. This field will be deserialized only if the expr is true. Warning: "expr" is not checked on serializing, no extra bool value in this case.
```rust
5. Length can be u16 or [VLQ](https://en.wikipedia.org/wiki/Variable-length_quantity) with features (u32 by default)
toml
resend = {version = "0.1", features = ["little", "len16"]}
resend = {version = "0.1", features = ["big", "lenvlq"]}
```
toml
resend = {version = "0.1", features = ["little", "len_16", "MAX_LEN_100M"]}
For example, you want a string with variable-length quantity
```rust pub struct VarLenString (pub String);
impl Sendable for VarLenString {
fn sndto(&self, writer: &mut S) -> io::Result<()>
where
S: resend::Sender {
writer.snd(resend::endian::VLQ(self.0.len()))?;
writer.sndall(self.0.as_bytes())
}
}
impl Receivable for VarLenString {
fn rcvfrom
rust
use resend::endian::{Ascii, UTF16, UTF16Char, VLQ};
Implements resend::FromReader and resend::IntoWriter if you need the "len(fieldname)" attribute working on your type. For example:
```rust
impl FromReader for Vec
impl IntoWriter for Vec
let b = &self[..l];
writer.snd_all(b)?;
if left > 0 {
writer.snd_all(&vec![0; left])?;
}
Ok(())
}
} ```
String, Ascii and UTF16 with #[len(fieldnameor_const)] attribute: if the specified length is bigger then the actual length: extra '\0' will be appended when it's serialized, and extra '\0' will be removed after it's deserialized; if the specified length is smaller, the string will be truncated to that length. This is useful if you need null terminated, fixed length string.
Convert int to Enum
rust
//Conver little-endian u16 to Blue ("little" feature)
//[u8] doesn't implement Read, convert it to &[u8] with as_ref()
let c: Color = [32_u8, 0].as_ref().rcv()?;
Use enumeration to serialize Object Oriented classes: ```Rust //type value (enum tag value) after the parent class struct YourObject { parent: ParentClass, child: EnumOfChildClass, } //type value (enum tag value) before the parent class struct Child { parent: ParentClass, child_field, ... } enum { child1, child2, }
``` 4. resend::endian:Length handles 3 types: u32, u16, VLQ. It's better to use this Length type directly in your object.
MIT OR Apache-2.0
This library is developed for Remote Spark Corp's RDP (Remote Desktop Protocol) Project.