An open API service indexing awesome lists of open source software.

https://github.com/haxelion/bytepack

A byte packing crate for rust
https://github.com/haxelion/bytepack

crate data io rust

Last synced: 10 months ago
JSON representation

A byte packing crate for rust

Awesome Lists containing this project

README

          

bytepack
========

[![Crates.io](https://img.shields.io/crates/v/bytepack.svg)](https://crates.io/crates/bytepack)
[![Build Status](https://travis-ci.org/haxelion/bytepack.svg?branch=master)](https://travis-ci.org/haxelion/bytepack)
[![Docs.rs](https://docs.rs/bytepack/badge.svg)](https://docs.rs/bytepack)

`bytepack` is a simple crate which extends the `std::io` API to be able to read and write any
data type in their memory representation. It can be seen as a generalization of the
`std::io::Read` and `std::io::Write` trait , but operating on a generic parameter `T` instead
of `u8`. This crate focus on performances by beeing no copy (except in one clearly marked case)
and offering methods to read and write arrays.

`bytepack` offers three trait famillies allowing different endianness control.
`Unpacker` and `Packer` read and write data in the endianness of the operating system. `LEUnpacker`
and `LEPacker` always read and write data in little endian while `BEUnpacker` and `BEPacker` do the
same in big endian. They all conform to the same API which is copied from the one of `std::io`.
This means switching from one endianness to another can be done by simply bringing a different
trait in scope.

Because `bytepack` is not a serialization library, it cannot read and write complex types like
`Vec`, `Rc`, etc. directly from a Reader or to Writer. Indeed those types do not contain the
underlying data directly packed inside but rather hold a reference or a pointer to it. To
identify types which holds their data "packed" together, the `Packed` trait is used. Additionnaly
it provides a in-place endianness switching method. One can implement this trait for the data types
deemed safe to read and write. An automatic derive for structures made only of types implementing
`Packed` is also implemented in the [`bytepack_derive`](https://github.com/haxelion/bytepack_derive)
crate.

Examples
--------

Here are two functions which can serialize and deserialize a `Vec`:

``` rust
extern crate bytepack;

use std::fs::File;
use std::iter::repeat;

use bytepack::{LEPacker, LEUnpacker};

fn write_samples(file: &str, samples: &Vec) {
let mut file = File::create(file).unwrap();
file.pack(samples.len() as u32).unwrap();
file.pack_all(&samples[..]).unwrap();
}

fn read_samples(file: &str) -> Vec {
let mut file = File::open(file).unwrap();
let num_samples : u32 = file.unpack().unwrap();
let mut samples : Vec = repeat(0f32).take(num_samples as usize).collect();
file.unpack_exact(&mut samples[..]).unwrap();
return samples;
}
```

Thanks to the genericity of the `Packed` trait we could make the previous function generic:

``` rust
extern crate bytepack;

use std::fs::File;

use bytepack::{LEPacker, Packed};

fn write_vec(file: &str, samples: &Vec) {
let mut file = File::create(file).unwrap();
file.pack(samples.len() as u32).unwrap();
file.pack_all(&samples[..]).unwrap();
}
```

Because we can derive Packed for our own struct, we can use them with our own types:

``` rust
extern crate bytepack;
#[macro_use]
extern crate bytepack_derive;

use std::fs::File;

use bytepack::{LEPacker, Packed};

#[derive(Packed, Clone)]
struct Vertex {
x: T,
y: T,
z: T
}

fn write_vec(file: &str, samples: &Vec) {
let mut file = File::create(file).unwrap();
file.pack(samples.len() as u32).unwrap();
file.pack_all(&samples[..]).unwrap();
}

fn main() {
let square : Vec> = vec![
Vertex{x: 0.0, y: 0.0, z: 0.0},
Vertex{x: 1.0, y: 0.0, z: 0.0},
Vertex{x: 1.0, y: 1.0, z: 0.0},
Vertex{x: 0.0, y: 1.0, z: 0.0},
];

write_vec("square.raw", &square);
}
```