Skip to content

Commit

Permalink
Support Unit like structs for DekuWrite (#450)
Browse files Browse the repository at this point in the history
* Fix support for DekuWrite by not adding fields to the struct destruction
  in deku-write proc-macro
* Add test

Closes #449
  • Loading branch information
wcampbell0x2a authored Jun 14, 2024
1 parent 7031451 commit a9e2d1d
Show file tree
Hide file tree
Showing 3 changed files with 24 additions and 2 deletions.
3 changes: 2 additions & 1 deletion deku-derive/src/macros/deku_write.rs
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ fn emit_struct(input: &DekuData) -> Result<TokenStream, syn::Error> {
let field_updates = emit_field_updates(&fields, Some(quote! { self. }));

let named = fields.style.is_struct();
let unit = fields.style.is_unit();

let field_idents = fields.iter().enumerate().filter_map(|(i, f)| {
if !f.temp {
Expand All @@ -43,7 +44,7 @@ fn emit_struct(input: &DekuData) -> Result<TokenStream, syn::Error> {
}
});

let destructured = gen_struct_destruction(named, &input.ident, field_idents);
let destructured = gen_struct_destruction(named, unit, &input.ident, field_idents);

// Implement `DekuContainerWrite` for types that don't need a context
if input.ctx.is_none() || (input.ctx.is_some() && input.ctx_default.is_some()) {
Expand Down
7 changes: 6 additions & 1 deletion deku-derive/src/macros/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -95,10 +95,15 @@ fn gen_struct_init<I: ToTokens>(
/// - Unnamed: `#ident ( ref fields )`
fn gen_struct_destruction<I: ToTokens, F: ToTokens>(
named: bool,
unit: bool,
ident: I,
field_idents: impl Iterator<Item = F>,
) -> TokenStream {
if named {
if unit {
quote! {
#ident
}
} else if named {
quote! {
#ident {
#(ref #field_idents),*
Expand Down
16 changes: 16 additions & 0 deletions tests/test_struct.rs
Original file line number Diff line number Diff line change
Expand Up @@ -204,3 +204,19 @@ fn test_big_endian() {
let new_bytes = a.to_bytes().unwrap();
assert_eq!(&bytes[..2], &*new_bytes);
}

#[test]
fn test_units() {
#[derive(DekuRead, DekuWrite)]
#[deku(magic = b"\xf0")]
struct Unit;

let bytes = [0xf0];
let a = Unit::from_bytes((&bytes, 0)).unwrap().1;
let new_bytes = a.to_bytes().unwrap();
assert_eq!(bytes, &*new_bytes);

let a = Unit;
let new_bytes = a.to_bytes().unwrap();
assert_eq!(bytes, &*new_bytes);
}

0 comments on commit a9e2d1d

Please sign in to comment.