diff options
author | Nadrieril | 2019-04-06 17:55:43 +0200 |
---|---|---|
committer | Nadrieril | 2019-04-06 17:57:53 +0200 |
commit | 42d0f8100462f8a17a3ba1b86664310cdb71dfdc (patch) | |
tree | 202199956ed8d7497e0bd986f22473b3e92cf8f9 /dhall_generator/src/dhall_type.rs | |
parent | d9b4bd8d4019ca9ab999c0c4657663604158101c (diff) |
Rename some modules
Diffstat (limited to 'dhall_generator/src/dhall_type.rs')
-rw-r--r-- | dhall_generator/src/dhall_type.rs | 173 |
1 files changed, 0 insertions, 173 deletions
diff --git a/dhall_generator/src/dhall_type.rs b/dhall_generator/src/dhall_type.rs deleted file mode 100644 index 38c871d..0000000 --- a/dhall_generator/src/dhall_type.rs +++ /dev/null @@ -1,173 +0,0 @@ -extern crate proc_macro; -// use dhall_core::*; -use proc_macro::TokenStream; -use quote::{quote, quote_spanned}; -use syn::spanned::Spanned; -use syn::Error; -use syn::{parse_quote, DeriveInput}; - -pub fn derive_type(input: TokenStream) -> TokenStream { - TokenStream::from(match derive_type_inner(input) { - Ok(tokens) => tokens, - Err(err) => err.to_compile_error(), - }) -} - -pub fn derive_for_struct( - data: &syn::DataStruct, - constraints: &mut Vec<syn::Type>, -) -> Result<proc_macro2::TokenStream, Error> { - let fields = match &data.fields { - syn::Fields::Named(fields) => fields - .named - .iter() - .map(|f| { - let name = f.ident.as_ref().unwrap().to_string(); - let ty = &f.ty; - (name, ty) - }) - .collect(), - syn::Fields::Unnamed(fields) => fields - .unnamed - .iter() - .enumerate() - .map(|(i, f)| { - let name = format!("_{}", i + 1); - let ty = &f.ty; - (name, ty) - }) - .collect(), - syn::Fields::Unit => vec![], - }; - let fields = fields - .into_iter() - .map(|(name, ty)| { - let name = dhall_core::Label::from(name); - constraints.push(ty.clone()); - (name, quote!(<#ty as dhall::StaticType>::get_type())) - }) - .collect(); - let record = - crate::dhall_expr::quote_exprf(dhall_core::ExprF::RecordType(fields)); - Ok(quote! { dhall_core::rc(#record) }) -} - -pub fn derive_for_enum( - data: &syn::DataEnum, - constraints: &mut Vec<syn::Type>, -) -> Result<proc_macro2::TokenStream, Error> { - let variants = data - .variants - .iter() - .map(|v| { - let name = dhall_core::Label::from(v.ident.to_string()); - let ty = match &v.fields { - syn::Fields::Unnamed(fields) if fields.unnamed.is_empty() => { - Err(Error::new( - v.span(), - "Nullary variants are not supported", - )) - } - syn::Fields::Unnamed(fields) if fields.unnamed.len() > 1 => { - Err(Error::new( - v.span(), - "Variants with more than one field are not supported", - )) - } - syn::Fields::Unnamed(fields) => { - Ok(&fields.unnamed.iter().next().unwrap().ty) - } - syn::Fields::Named(_) => Err(Error::new( - v.span(), - "Named variants are not supported", - )), - syn::Fields::Unit => Err(Error::new( - v.span(), - "Nullary variants are not supported", - )), - }; - let ty = ty?; - constraints.push(ty.clone()); - Ok((name, quote!(<#ty as dhall::StaticType>::get_type()))) - }) - .collect::<Result<_, Error>>()?; - - let union = - crate::dhall_expr::quote_exprf(dhall_core::ExprF::UnionType(variants)); - Ok(quote! { dhall_core::rc(#union) }) -} - -pub fn derive_type_inner( - input: TokenStream, -) -> Result<proc_macro2::TokenStream, Error> { - let input: DeriveInput = syn::parse_macro_input::parse(input)?; - - // List of types that must impl Type - let mut constraints = vec![]; - - let get_type = match &input.data { - syn::Data::Struct(data) => derive_for_struct(data, &mut constraints)?, - syn::Data::Enum(data) if data.variants.is_empty() => { - return Err(Error::new( - input.span(), - "Empty enums are not supported", - )) - } - syn::Data::Enum(data) => derive_for_enum(data, &mut constraints)?, - syn::Data::Union(x) => { - return Err(Error::new( - x.union_token.span(), - "Unions are not supported", - )) - } - }; - - let mut generics = input.generics.clone(); - generics.make_where_clause(); - let (impl_generics, ty_generics, orig_where_clause) = - generics.split_for_impl(); - let orig_where_clause = orig_where_clause.unwrap(); - - // Hygienic errors - let assertions = constraints.iter().enumerate().map(|(i, ty)| { - // Ensure that ty: Type, with an appropriate span - let assert_name = - syn::Ident::new(&format!("_AssertType{}", i), ty.span()); - let mut local_where_clause = orig_where_clause.clone(); - local_where_clause - .predicates - .push(parse_quote!(#ty: dhall::StaticType)); - let phantoms = generics.params.iter().map(|param| match param { - syn::GenericParam::Type(syn::TypeParam { ident, .. }) => { - quote!(#ident) - } - syn::GenericParam::Lifetime(syn::LifetimeDef { - lifetime, .. - }) => quote!(&#lifetime ()), - _ => unimplemented!(), - }); - quote_spanned! {ty.span()=> - struct #assert_name #impl_generics #local_where_clause { - _phantom: std::marker::PhantomData<(#(#phantoms),*)> - }; - } - }); - - // Ensure that all the fields have a Type impl - let mut where_clause = orig_where_clause.clone(); - for ty in constraints.iter() { - where_clause.predicates.push(parse_quote!(#ty: dhall::StaticType)); - } - - let ident = &input.ident; - let tokens = quote! { - impl #impl_generics dhall::StaticType for #ident #ty_generics - #where_clause { - fn get_type() -> dhall_core::DhallExpr { - #(#assertions)* - #get_type - } - } - }; - Ok(tokens) -} |