Handwrite boilerplate impls for Type

This allows dropping the Span wrapper that was only needed for the Eq
and Hash support.
diff --git a/syntax/impls.rs b/syntax/impls.rs
index 8153f03..741431a 100644
--- a/syntax/impls.rs
+++ b/syntax/impls.rs
@@ -1,5 +1,36 @@
-use crate::syntax::{Ref, Ty1};
+use crate::syntax::{Ref, Ty1, Type};
 use std::hash::{Hash, Hasher};
+use std::mem;
+
+impl Hash for Type {
+    fn hash<H: Hasher>(&self, state: &mut H) {
+        mem::discriminant(self).hash(state);
+        match self {
+            Type::Ident(t) => t.hash(state),
+            Type::RustBox(t) => t.hash(state),
+            Type::UniquePtr(t) => t.hash(state),
+            Type::Ref(t) => t.hash(state),
+            Type::Str(t) => t.hash(state),
+            Type::Void(_) => {}
+        }
+    }
+}
+
+impl Eq for Type {}
+
+impl PartialEq for Type {
+    fn eq(&self, other: &Type) -> bool {
+        match (self, other) {
+            (Type::Ident(lhs), Type::Ident(rhs)) => lhs == rhs,
+            (Type::RustBox(lhs), Type::RustBox(rhs)) => lhs == rhs,
+            (Type::UniquePtr(lhs), Type::UniquePtr(rhs)) => lhs == rhs,
+            (Type::Ref(lhs), Type::Ref(rhs)) => lhs == rhs,
+            (Type::Str(lhs), Type::Str(rhs)) => lhs == rhs,
+            (Type::Void(_), Type::Void(_)) => true,
+            (_, _) => false,
+        }
+    }
+}
 
 impl Eq for Ty1 {}
 
diff --git a/syntax/mod.rs b/syntax/mod.rs
index e702be0..39198cc 100644
--- a/syntax/mod.rs
+++ b/syntax/mod.rs
@@ -65,7 +65,6 @@
     pub ident: Ident,
 }
 
-#[derive(Hash, Eq, PartialEq)]
 pub enum Type {
     Ident(Ident),
     RustBox(Box<Ty1>),