Skip to content

Commit

Permalink
attempt to add primitive types
Browse files Browse the repository at this point in the history
Signed-off-by: Eval EXEC <execvy@gmail.com>
  • Loading branch information
eval-exec committed Mar 22, 2023
1 parent 7e7e2ad commit 263612d
Show file tree
Hide file tree
Showing 28 changed files with 455 additions and 58 deletions.
16 changes: 6 additions & 10 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
ci:
@set -eu; \
export RUSTFLAGS='-D warnings'; \
make fmt clippy; \
make cargo-test ci-examples ci-crates; \
make fmt clippy check; \
make ci-examples ci-crates; \
echo "Success!"

RUST_DEV_PROJS = examples/ci-tests tests
Expand All @@ -23,6 +23,10 @@ clean:
cd - > /dev/null; \
done

check:
@set -eu; \
diff std/rust/primitive_types.mol tools/codegen/primitive_types.mol

fmt:
@set -eu; \
for dir in ${RUST_PROJS}; do \
Expand All @@ -40,14 +44,6 @@ clippy:
cd - > /dev/null; \
done

cargo-test:
@set -eu; \
for dir in ${RUST_PROJS}; do \
cd "$${dir}"; \
cargo test; \
cd - > /dev/null; \
done


ci-msrv:
@set -eu; \
Expand Down
2 changes: 1 addition & 1 deletion bindings/rust/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "molecule"
version = "0.7.5"
version = "0.8.0"
authors = ["Nervos Core Dev <dev@nervos.org>"]
edition = "2018"
description = "Rust bindings for molecule."
Expand Down
2 changes: 1 addition & 1 deletion bindings/rust/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ cfg_if::cfg_if! {

pub mod error;
pub mod prelude;
mod primitive;
pub mod primitive;

// Little Endian
pub type Number = u32;
Expand Down
3 changes: 3 additions & 0 deletions std/rust/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
target/
Cargo.lock

30 changes: 30 additions & 0 deletions std/rust/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
[package]
name = "molecule-std"
version = "0.0.1"
authors = ["Nervos Core Dev <dev@nervos.org>"]
edition = "2018"
description = "std primitive types for molecule."
homepage = "https://github.com/nervosnetwork/molecule"
repository = "https://github.com/nervosnetwork/molecule"
keywords = ["molecule", "code-generation", "serialization"]
categories = [
"parser-implementations",
"development-tools::build-utils",
"encoding",
"data-structures"
]
license = "MIT"

# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html

[dependencies]
molecule = { path = "../../bindings/rust" }

[features]
default = ["std"]
with-primitive-types = []
std = ["molecule/bytes", "molecule/faster-hex"]

[build-dependencies]
codegen = {package ="molecule-codegen", version = "=0.8.0", path = "../../tools/codegen" }

20 changes: 20 additions & 0 deletions std/rust/build.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
use codegen::{Compiler, Language};

fn compile_schema(schema: &str) {
let mut compiler = Compiler::new();
compiler
.input_schema_file(schema)
.generate_code(Language::Rust)
.output_dir_set_default()
.expand_primitive(true)
.run()
.unwrap();
println!("cargo:rerun-if-changed={}", schema);
}

fn main() {
println!("cargo:rerun-if-changed=primitive_types.mol");
compile_schema("primitive_types.mol");
let out_dir = ::std::env::var("OUT_DIR").unwrap();
println!("{}", out_dir);
}
14 changes: 14 additions & 0 deletions std/rust/primitive_types.mol
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
// Unsigned integers
array uint64 [byte; 8];
array uint32 [byte; 4];
array uint16 [byte; 2];
array uint8 [byte; 1];

// Signed integers
array int64 [byte; 8];
array int32 [byte; 4];
array int16 [byte; 2];
array int8 [byte; 1];

// Bool
array bool [byte; 1];
35 changes: 35 additions & 0 deletions std/rust/src/lib.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
pub use crate as molecule_std;

pub use molecule::*;

#[cfg(feature = "with-primitive-types")]
pub mod primitives {
include!(concat!(env!("OUT_DIR"), "/primitive_types.rs"));
}

pub mod prelude {
pub use molecule::prelude::*;

#[cfg(feature = "with-primitive-types")]
pub use crate::primitives::*;
}

#[cfg(feature = "with-primitive-types")]
mod primitives_pack;

pub mod pack {
use crate::prelude::Entity;
pub trait Unpack<T> {
/// Unpack binary data into rust types.
fn unpack(&self) -> T;
}

/// A syntactic sugar to convert a rust type into binary data.
pub trait Pack<T: Entity> {
/// Packs a rust type into binary data.
fn pack(&self) -> T;
}

#[cfg(feature = "with-primitive-types")]
pub use crate::primitives_pack::*;
}
154 changes: 154 additions & 0 deletions std/rust/src/primitives_pack.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,154 @@
use crate::bytes::*;
use crate::pack::*;
use crate::prelude::*;

macro_rules! impl_conversion_for_entity_unpack {
($original:ty, $entity:ident) => {
impl Unpack<$original> for $entity {
fn unpack(&self) -> $original {
self.as_reader().unpack()
}
}
};
}

impl Pack<Uint64> for u64 {
fn pack(&self) -> Uint64 {
Uint64::new_unchecked(Bytes::from(self.to_le_bytes().to_vec()))
}
}

impl<'r> Unpack<u64> for Uint64Reader<'r> {
fn unpack(&self) -> u64 {
let mut b = [0u8; 8];
b.copy_from_slice(self.as_slice());
u64::from_le_bytes(b)
}
}
impl_conversion_for_entity_unpack!(u64, Uint64);

impl Pack<Uint32> for u32 {
fn pack(&self) -> Uint32 {
Uint32::new_unchecked(Bytes::from(self.to_le_bytes().to_vec()))
}
}

impl<'r> Unpack<u32> for Uint32Reader<'r> {
fn unpack(&self) -> u32 {
let mut b = [0u8; 4];
b.copy_from_slice(self.as_slice());
u32::from_le_bytes(b)
}
}
impl_conversion_for_entity_unpack!(u32, Uint32);

impl Pack<Uint16> for u16 {
fn pack(&self) -> Uint16 {
Uint16::new_unchecked(Bytes::from(self.to_le_bytes().to_vec()))
}
}

impl<'r> Unpack<u16> for Uint16Reader<'r> {
fn unpack(&self) -> u16 {
let mut b = [0u8; 2];
b.copy_from_slice(self.as_slice());
u16::from_le_bytes(b)
}
}
impl_conversion_for_entity_unpack!(u16, Uint16);

impl Pack<Uint8> for u8 {
fn pack(&self) -> Uint8 {
Uint8::new_unchecked(Bytes::from(self.to_le_bytes().to_vec()))
}
}

impl<'r> Unpack<u8> for Uint8Reader<'r> {
fn unpack(&self) -> u8 {
let mut b = [0u8; 1];
b.copy_from_slice(self.as_slice());
u8::from_le_bytes(b)
}
}
impl_conversion_for_entity_unpack!(u8, Uint8);

// Signed integers

impl Pack<Int64> for i64 {
fn pack(&self) -> Int64 {
Int64::new_unchecked(Bytes::from(self.to_le_bytes().to_vec()))
}
}

impl<'r> Unpack<i64> for Int64Reader<'r> {
fn unpack(&self) -> i64 {
let mut b = [0u8; 8];
b.copy_from_slice(self.as_slice());
i64::from_le_bytes(b)
}
}
impl_conversion_for_entity_unpack!(i64, Int64);

impl Pack<Int32> for i32 {
fn pack(&self) -> Int32 {
Int32::new_unchecked(Bytes::from(self.to_le_bytes().to_vec()))
}
}

impl<'r> Unpack<i32> for Int32Reader<'r> {
fn unpack(&self) -> i32 {
let mut b = [0u8; 4];
b.copy_from_slice(self.as_slice());
i32::from_le_bytes(b)
}
}
impl_conversion_for_entity_unpack!(i32, Int32);

impl Pack<Int16> for i16 {
fn pack(&self) -> Int16 {
Int16::new_unchecked(Bytes::from(self.to_le_bytes().to_vec()))
}
}

impl<'r> Unpack<i16> for Int16Reader<'r> {
fn unpack(&self) -> i16 {
let mut b = [0u8; 2];
b.copy_from_slice(self.as_slice());
i16::from_le_bytes(b)
}
}
impl_conversion_for_entity_unpack!(i16, Int16);

impl Pack<Int8> for i8 {
fn pack(&self) -> Int8 {
Int8::new_unchecked(Bytes::from(self.to_le_bytes().to_vec()))
}
}

impl<'r> Unpack<i8> for Int8Reader<'r> {
fn unpack(&self) -> i8 {
let mut b = [0u8; 1];
b.copy_from_slice(self.as_slice());
i8::from_le_bytes(b)
}
}
impl_conversion_for_entity_unpack!(i8, Int8);

// Bool
impl Pack<Bool> for bool {
fn pack(&self) -> Bool {
let b = u8::from(*self);
Bool::new_unchecked(Bytes::from(vec![b]))
}
}

impl<'r> Unpack<bool> for BoolReader<'r> {
fn unpack(&self) -> bool {
match self.as_slice()[0] {
0 => false,
1 => true,
_ => unreachable!(),
}
}
}
impl_conversion_for_entity_unpack!(bool, Bool);
8 changes: 7 additions & 1 deletion tools/codegen/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "molecule-codegen"
version = "0.7.5"
version = "0.8.0"
authors = ["Nervos Core Dev <dev@nervos.org>"]
edition = "2018"
description = "Code generator for molecule."
Expand All @@ -16,7 +16,13 @@ categories = [
license = "MIT"

[dependencies]
<<<<<<< HEAD
molecule = { version = "=0.7.5", path = "../../bindings/rust", default-features = false }
||||||| parent of ac0aeb8 (attempt to add primitive types)
molecule = { version = "=0.7.3", path = "../../bindings/rust", default-features = false }
=======
molecule = { version = "=0.8.0", path = "../../bindings/rust", default-features = false }
>>>>>>> ac0aeb8 (attempt to add primitive types)
property = "0.3.3"
pest = "2.1.3"
pest_derive = "2.1.0"
Expand Down
14 changes: 14 additions & 0 deletions tools/codegen/primitive_types.mol
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
// Unsigned integers
array uint64 [byte; 8];
array uint32 [byte; 4];
array uint16 [byte; 2];
array uint8 [byte; 1];

// Signed integers
array int64 [byte; 8];
array int32 [byte; 4];
array int16 [byte; 2];
array int8 [byte; 1];

// Bool
array bool [byte; 1];
4 changes: 2 additions & 2 deletions tools/codegen/src/ast/raw/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ pub(crate) struct UnionDecl {
imported_depth: usize,
}

#[derive(Debug, Property)]
#[derive(Debug, Property, Clone)]
pub(crate) struct ArrayDecl {
name: String,
item: ItemDecl,
Expand Down Expand Up @@ -94,7 +94,7 @@ pub(crate) struct TableDecl {
imported_depth: usize,
}

#[derive(Debug, Property)]
#[derive(Debug, Property, Clone)]
pub(crate) struct ItemDecl {
typ: String,
}
Expand Down
Loading

0 comments on commit 263612d

Please sign in to comment.