Skip to content

Commit

Permalink
support deriving Zeroable for fieldless enums (Lokathor#233)
Browse files Browse the repository at this point in the history
* support deriving Zeroable for fieldless enums

* add test for deriving Zeroable on enum
  • Loading branch information
Freax13 authored and zachs18 committed Jun 6, 2024
1 parent 62f1a5e commit a66c79c
Show file tree
Hide file tree
Showing 2 changed files with 43 additions and 7 deletions.
42 changes: 35 additions & 7 deletions bytemuck_derive/src/traits.rs
Original file line number Diff line number Diff line change
Expand Up @@ -127,15 +127,43 @@ impl Derivable for Zeroable {
Ok(syn::parse_quote!(#crate_name::Zeroable))
}

fn asserts(
input: &DeriveInput, crate_name: &TokenStream,
) -> Result<TokenStream> {
fn check_attributes(ty: &Data, attributes: &[Attribute]) -> Result<()> {
let repr = get_repr(attributes)?;
match ty {
Data::Struct(_) => Ok(()),
Data::Enum(DataEnum { variants,.. }) => {
if !repr.repr.is_integer() {
bail!("Zeroable requires the enum to be an explicit #[repr(Int)]")
}

if variants.iter().any(|variant| !variant.fields.is_empty()) {
bail!("Only fieldless enums are supported for Zeroable")
}

let iter = VariantDiscriminantIterator::new(variants.iter());
let mut has_zero_variant = false;
for res in iter {
let discriminant = res?;
if discriminant == 0 {
has_zero_variant = true;
break;
}
}
if !has_zero_variant {
bail!("No variant's discriminant is 0")
}

Ok(())
},
Data::Union(_) => Ok(())
}
}

fn asserts(input: &DeriveInput, crate_name: &TokenStream) -> Result<TokenStream> {
match &input.data {
Data::Union(_) => Ok(quote!()), // unions are always `Zeroable`
Data::Struct(_) => {
generate_fields_are_trait(input, Self::ident(input, crate_name)?)
}
Data::Enum(_) => bail!("Deriving Zeroable is not supported for enums"),
Data::Struct(_) => generate_fields_are_trait(input, Self::ident(input, crate_name)?),
Data::Enum(_) => Ok(quote!()),
}
}

Expand Down
8 changes: 8 additions & 0 deletions bytemuck_derive/tests/basic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,14 @@ struct ZeroGeneric<T: bytemuck::Zeroable> {
a: T,
}

#[derive(Zeroable)]
#[repr(u8)]
enum ZeroEnum {
A = 0,
B = 1,
C = 2,
}

#[derive(TransparentWrapper)]
#[repr(transparent)]
struct TransparentSingle {
Expand Down

0 comments on commit a66c79c

Please sign in to comment.