From e1792223cb279abc42db1709a4ba2c0423da3f24 Mon Sep 17 00:00:00 2001 From: fi3 Date: Mon, 19 Aug 2024 11:03:54 +0200 Subject: [PATCH] Add support for data types defined by sv2 extensions In no-serde-sv2 an sv2 sequence is generic over T. If we want this sequence to be Deserialize we need T to be Fixed and GerMarker. This 2 traits were private since all the sv2 types are already defined in no-serde-sv2. But if we want to use sv2 types defined in an sv2 extensions we need to make these traits public. The Encodable dervive macro in derive_codec implement GetSize for the passed struct. But GetSize is also a blanket implementation for every type that implement Fixed. So if we implement Fixed for our new sv2 type and then we derive Encodable (commonly renamed Serialize) we get an error. This commit add an attribute to Encodable called already_sized if the struct that we want derive Encodable is market as already_sized the macro will not implement GetSize for it. This commit also bump minor version of derive_codec and no-serde-sv2 consequentially also of binary-sv2 since it reexport the above libs. --- protocols/Cargo.lock | 6 +- protocols/v2/binary-sv2/binary-sv2/Cargo.toml | 2 +- .../binary-sv2/no-serde-sv2/codec/Cargo.toml | 2 +- .../binary-sv2/no-serde-sv2/codec/src/lib.rs | 4 +- .../no-serde-sv2/derive_codec/Cargo.toml | 2 +- .../no-serde-sv2/derive_codec/src/lib.rs | 59 +++++++++++++------ roles/Cargo.lock | 4 +- 7 files changed, 50 insertions(+), 29 deletions(-) diff --git a/protocols/Cargo.lock b/protocols/Cargo.lock index 9e04903ff2..1f853f4ad9 100644 --- a/protocols/Cargo.lock +++ b/protocols/Cargo.lock @@ -77,7 +77,7 @@ checksum = "d86b93f97252c47b41663388e6d155714a9d0c398b99f1005cbc5f978b29f445" [[package]] name = "binary_codec_sv2" -version = "1.0.0" +version = "1.1.0" dependencies = [ "buffer_sv2", "quickcheck", @@ -85,7 +85,7 @@ dependencies = [ [[package]] name = "binary_sv2" -version = "1.0.1" +version = "1.1.0" dependencies = [ "binary_codec_sv2", "derive_codec_sv2", @@ -260,7 +260,7 @@ dependencies = [ [[package]] name = "derive_codec_sv2" -version = "1.0.0" +version = "1.1.0" dependencies = [ "binary_codec_sv2", ] diff --git a/protocols/v2/binary-sv2/binary-sv2/Cargo.toml b/protocols/v2/binary-sv2/binary-sv2/Cargo.toml index 1fd78fcc19..b8742ad48e 100644 --- a/protocols/v2/binary-sv2/binary-sv2/Cargo.toml +++ b/protocols/v2/binary-sv2/binary-sv2/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "binary_sv2" -version = "1.0.1" +version = "1.1.0" authors = ["fi3 "] edition = "2018" description = "Sv2 data format" diff --git a/protocols/v2/binary-sv2/no-serde-sv2/codec/Cargo.toml b/protocols/v2/binary-sv2/no-serde-sv2/codec/Cargo.toml index 5f1f83e129..d564c96be8 100644 --- a/protocols/v2/binary-sv2/no-serde-sv2/codec/Cargo.toml +++ b/protocols/v2/binary-sv2/no-serde-sv2/codec/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "binary_codec_sv2" -version = "1.0.0" +version = "1.1.0" authors = ["fi3 "] edition = "2018" description = "Sv2 data format" diff --git a/protocols/v2/binary-sv2/no-serde-sv2/codec/src/lib.rs b/protocols/v2/binary-sv2/no-serde-sv2/codec/src/lib.rs index 8f7d96e62f..8fe893da83 100644 --- a/protocols/v2/binary-sv2/no-serde-sv2/codec/src/lib.rs +++ b/protocols/v2/binary-sv2/no-serde-sv2/codec/src/lib.rs @@ -30,9 +30,9 @@ pub use datatypes::{ }; pub use crate::codec::{ - decodable::Decodable, + decodable::{Decodable, GetMarker}, encodable::{Encodable, EncodableField}, - GetSize, SizeHint, + Fixed, GetSize, SizeHint, }; #[allow(clippy::wrong_self_convention)] diff --git a/protocols/v2/binary-sv2/no-serde-sv2/derive_codec/Cargo.toml b/protocols/v2/binary-sv2/no-serde-sv2/derive_codec/Cargo.toml index 62e62bd9c8..93f202d8bd 100644 --- a/protocols/v2/binary-sv2/no-serde-sv2/derive_codec/Cargo.toml +++ b/protocols/v2/binary-sv2/no-serde-sv2/derive_codec/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "derive_codec_sv2" -version = "1.0.0" +version = "1.1.0" authors = ["fi3 "] edition = "2018" description = "Derive macro for Sv2 binary format serializer and deserializer" diff --git a/protocols/v2/binary-sv2/no-serde-sv2/derive_codec/src/lib.rs b/protocols/v2/binary-sv2/no-serde-sv2/derive_codec/src/lib.rs index 6821abb6ae..aef883ba1b 100644 --- a/protocols/v2/binary-sv2/no-serde-sv2/derive_codec/src/lib.rs +++ b/protocols/v2/binary-sv2/no-serde-sv2/derive_codec/src/lib.rs @@ -2,6 +2,24 @@ extern crate proc_macro; use core::iter::FromIterator; use proc_macro::{Group, TokenStream, TokenTree}; +fn is_already_sized(item: TokenStream) -> bool { + let stream = item.into_iter(); + + for next in stream { + if let TokenTree::Group(g) = next.clone() { + if g.delimiter() == proc_macro::Delimiter::Bracket { + for t in g.stream().into_iter() { + if let TokenTree::Ident(i) = t { + if i.to_string() == "already_sized" { + return true; + } + } + } + } + } + } + false +} fn remove_attributes(item: TokenStream) -> TokenStream { let stream = item.into_iter(); let mut is_attribute = false; @@ -356,8 +374,9 @@ fn get_static_generics(gen: &str) -> &str { } } -#[proc_macro_derive(Encodable)] +#[proc_macro_derive(Encodable, attributes(already_sized))] pub fn encodable(item: TokenStream) -> TokenStream { + let is_already_sized = is_already_sized(item.clone()); let parsed_struct = get_struct_properties(item); let fields = parsed_struct.fields.clone(); @@ -392,6 +411,23 @@ pub fn encodable(item: TokenStream) -> TokenStream { "<'decoder>".to_string() }; + let get_size = if is_already_sized { + String::new() + } else { + format!( + " + impl{} GetSize for {}{} {{ + fn get_size(&self) -> usize {{ + let mut size = 0; + {} + size + }} + }} + ", + impl_generics, parsed_struct.name, parsed_struct.generics, sizes + ) + }; + let result = format!( "mod impl_parse_encodable_{} {{ @@ -408,14 +444,7 @@ pub fn encodable(item: TokenStream) -> TokenStream { }} }} - - impl{} GetSize for {}{} {{ - fn get_size(&self) -> usize {{ - let mut size = 0; - {} - size - }} - }} + {} }}", // imports @@ -428,16 +457,8 @@ pub fn encodable(item: TokenStream) -> TokenStream { parsed_struct.name, parsed_struct.generics, field_into_decoded_field, - // impl Encodable for Struct - //impl{} Encodable<'decoder> for {}{} {{}} - //impl_generics, - //parsed_struct.name, - //parsed_struct.generics, - // impl GetSize for Struct - impl_generics, - parsed_struct.name, - parsed_struct.generics, - sizes, + // impl get_size + get_size, ); //println!("{}", result); diff --git a/roles/Cargo.lock b/roles/Cargo.lock index e0dfec0c14..d46de28ea6 100644 --- a/roles/Cargo.lock +++ b/roles/Cargo.lock @@ -373,14 +373,14 @@ checksum = "d86b93f97252c47b41663388e6d155714a9d0c398b99f1005cbc5f978b29f445" [[package]] name = "binary_codec_sv2" -version = "1.0.0" +version = "1.1.0" dependencies = [ "buffer_sv2", ] [[package]] name = "binary_sv2" -version = "1.0.1" +version = "1.1.0" dependencies = [ "binary_codec_sv2", "derive_codec_sv2",