Handle derives on shared enums
diff --git a/macro/src/derive.rs b/macro/src/derive.rs
index 3010dc6..8988012 100644
--- a/macro/src/derive.rs
+++ b/macro/src/derive.rs
@@ -1,4 +1,4 @@
-use crate::syntax::{Struct, Trait};
+use crate::syntax::{Enum, Struct, Trait};
 use proc_macro2::{Span, TokenStream};
 use quote::{quote, quote_spanned, ToTokens};
 
@@ -16,6 +16,36 @@
     expanded
 }
 
+pub fn expand_enum(enm: &Enum) -> TokenStream {
+    let mut expanded = TokenStream::new();
+    let mut has_copy = false;
+    let mut has_clone = false;
+
+    for derive in &enm.derives {
+        let span = derive.span;
+        match derive.what {
+            Trait::Copy => {
+                expanded.extend(enum_copy(enm, span));
+                has_copy = true;
+            }
+            Trait::Clone => {
+                expanded.extend(enum_clone(enm, span));
+                has_clone = true;
+            }
+        }
+    }
+
+    let span = enm.name.rust.span();
+    if !has_copy {
+        expanded.extend(enum_copy(enm, span));
+    }
+    if !has_clone {
+        expanded.extend(enum_clone(enm, span));
+    }
+
+    expanded
+}
+
 fn struct_copy(strct: &Struct, span: Span) -> TokenStream {
     let ident = &strct.name.rust;
 
@@ -55,3 +85,23 @@
         }
     }
 }
+
+fn enum_copy(enm: &Enum, span: Span) -> TokenStream {
+    let ident = &enm.name.rust;
+
+    quote_spanned! {span=>
+        impl ::std::marker::Copy for #ident {}
+    }
+}
+
+fn enum_clone(enm: &Enum, span: Span) -> TokenStream {
+    let ident = &enm.name.rust;
+
+    quote_spanned! {span=>
+        impl ::std::clone::Clone for #ident {
+            fn clone(&self) -> Self {
+                *self
+            }
+        }
+    }
+}
diff --git a/macro/src/expand.rs b/macro/src/expand.rs
index 09373ff..2917820 100644
--- a/macro/src/expand.rs
+++ b/macro/src/expand.rs
@@ -169,6 +169,7 @@
         // usable in patterns.
         #[derive(::std::cmp::PartialEq, ::std::cmp::Eq)]
     };
+    let derived_traits = derive::expand_enum(enm);
 
     quote! {
         #doc
@@ -188,13 +189,7 @@
             type Kind = ::cxx::kind::Trivial;
         }
 
-        impl ::std::marker::Copy for #ident {}
-
-        impl ::std::clone::Clone for #ident {
-            fn clone(&self) -> Self {
-                *self
-            }
-        }
+        #derived_traits
     }
 }
 
diff --git a/syntax/mod.rs b/syntax/mod.rs
index 17b290a..744963b 100644
--- a/syntax/mod.rs
+++ b/syntax/mod.rs
@@ -85,6 +85,7 @@
 
 pub struct Enum {
     pub doc: Doc,
+    pub derives: Vec<Derive>,
     pub enum_token: Token![enum],
     pub name: Pair,
     pub brace_token: Brace,
diff --git a/syntax/parse.rs b/syntax/parse.rs
index f1a330c..a009e19 100644
--- a/syntax/parse.rs
+++ b/syntax/parse.rs
@@ -126,6 +126,7 @@
     }
 
     let mut doc = Doc::new();
+    let mut derives = Vec::new();
     let mut repr = None;
     let mut namespace = namespace.clone();
     attrs::parse(
@@ -133,6 +134,7 @@
         &item.attrs,
         attrs::Parser {
             doc: Some(&mut doc),
+            derives: Some(&mut derives),
             repr: Some(&mut repr),
             namespace: Some(&mut namespace),
             ..Default::default()
@@ -188,6 +190,7 @@
 
     Ok(Api::Enum(Enum {
         doc,
+        derives,
         enum_token,
         name: Pair::new(namespace, item.ident),
         brace_token,