derive macro
This commit is contained in:
parent
61b34768e6
commit
e283a36945
@ -1,8 +1,49 @@
|
||||
use proc_macro::TokenStream;
|
||||
use syn::DeriveInput;
|
||||
use core::panic;
|
||||
|
||||
#[proc_macro_derive(PushPop)]
|
||||
use proc_macro::TokenStream;
|
||||
use quote::{quote, quote_spanned};
|
||||
use syn::{spanned::Spanned, DeriveInput};
|
||||
|
||||
#[proc_macro_derive(PushPopParse)]
|
||||
pub fn pushpop_derive_macro(item: TokenStream) -> TokenStream {
|
||||
let _ast: DeriveInput = syn::parse(item).unwrap();
|
||||
todo!()
|
||||
let ast: DeriveInput = syn::parse(item).unwrap();
|
||||
let struct_ident = ast.ident;
|
||||
let struct_data: syn::DataStruct = match ast.data {
|
||||
syn::Data::Struct(struct_data) => struct_data,
|
||||
syn::Data::Enum(_) => panic!("Error: Enum support not implemented"),
|
||||
syn::Data::Union(_) => panic!("Error: Union support not implemented"),
|
||||
};
|
||||
|
||||
let recursive = struct_data.fields.iter().map(|f| {
|
||||
let name = &f.ident;
|
||||
let ty = &f.ty;
|
||||
quote_spanned!(f.span()=> let #name = #ty::pop_ne_from(&mut source)?;)
|
||||
});
|
||||
|
||||
let names = struct_data.fields.iter().map(|f| {
|
||||
let name = &f.ident;
|
||||
quote_spanned!(f.span()=> #name)
|
||||
});
|
||||
let pop = struct_data.fields.iter().map(|f| {
|
||||
let name = &f.ident;
|
||||
quote_spanned!(f.span()=> PopFromNE::push_ne_into(&self.#name, dest)?;)
|
||||
});
|
||||
|
||||
quote!(
|
||||
impl PopFromNE for #struct_ident {
|
||||
fn pop_ne_from(mut source: &mut &[u8]) -> Result<Self>
|
||||
where
|
||||
Self: Sized,
|
||||
{
|
||||
#(#recursive)*
|
||||
Ok(#struct_ident{
|
||||
#(#names),*
|
||||
})
|
||||
}
|
||||
fn push_ne_into<T: Pushable>(&self, dest: &mut T) -> Result<()> {
|
||||
#(#pop)*
|
||||
Ok(())
|
||||
}
|
||||
})
|
||||
.into()
|
||||
}
|
||||
|
||||
28
src/lib.rs
28
src/lib.rs
@ -1,6 +1,5 @@
|
||||
use std::u16;
|
||||
|
||||
use anyhow::{Ok, Result};
|
||||
pub use poppable_derive::PushPopParse;
|
||||
|
||||
//pub type BytesRef = AsRef<u8>;
|
||||
|
||||
@ -236,3 +235,28 @@ flt_impl_pop_non_ne!(f32);
|
||||
|
||||
core_impl_pop_ne!(f64);
|
||||
flt_impl_pop_non_ne!(f64);
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn it_works() {
|
||||
let mut s: &[u8] = &vec![4, 8, 15, 16, 23, 42];
|
||||
let ans = u8::pop_ne_from(&mut s).unwrap();
|
||||
assert_eq!(ans, 4);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn derive_test() {
|
||||
#[derive(PushPopParse)]
|
||||
struct Thing {
|
||||
a: u8,
|
||||
b: u8,
|
||||
}
|
||||
let mut s: &[u8] = &vec![4, 8, 15, 16, 23, 42];
|
||||
let thing = Thing::pop_ne_from(&mut s).unwrap();
|
||||
assert_eq!(thing.a, 4);
|
||||
assert_eq!(thing.b, 8);
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user