summaryrefslogtreecommitdiff
path: root/dhall_generator
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--dhall_generator/src/dhall_expr.rs57
-rw-r--r--dhall_generator/src/dhall_type.rs4
-rw-r--r--dhall_generator/src/lib.rs13
3 files changed, 65 insertions, 9 deletions
diff --git a/dhall_generator/src/dhall_expr.rs b/dhall_generator/src/dhall_expr.rs
index 9da23b6..d0c5733 100644
--- a/dhall_generator/src/dhall_expr.rs
+++ b/dhall_generator/src/dhall_expr.rs
@@ -5,19 +5,29 @@ use proc_macro2::TokenStream;
use quote::quote;
use std::collections::BTreeMap;
-pub fn dhall_expr(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
+pub fn expr(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
let input_str = input.to_string();
let expr: SubExpr<X, Import> = parse_expr(&input_str).unwrap();
let no_import =
- |_: &Import| -> X { panic!("Don't use import in dhall!()") };
- let expr = rc(expr.as_ref().map_embed(&no_import));
- let output = quote_subexpr(&expr, &Context::new());
+ |_: &Import| -> X { panic!("Don't use import in dhall::expr!()") };
+ let expr = expr.as_ref().map_embed(&no_import);
+ let output = quote_expr(&expr, &Context::new());
+ output.into()
+}
+
+pub fn subexpr(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
+ let input_str = input.to_string();
+ let expr: SubExpr<X, Import> = parse_expr(&input_str).unwrap();
+ let no_import =
+ |_: &Import| -> X { panic!("Don't use import in dhall::subexpr!()") };
+ let expr = expr.as_ref().map_embed(&no_import);
+ let output = quote_subexpr(&rc(expr), &Context::new());
output.into()
}
// Returns an expression of type ExprF<T, _, _>, where T is the
// type of the subexpressions after interpolation.
-pub fn quote_expr<TS>(expr: ExprF<TS, Label, X, X>) -> TokenStream
+pub fn quote_exprf<TS>(expr: ExprF<TS, Label, X, X>) -> TokenStream
where
TS: quote::ToTokens + std::fmt::Debug,
{
@@ -134,7 +144,42 @@ fn quote_subexpr(
}
}
}
- e => bx(quote_expr(e)),
+ e => bx(quote_exprf(e)),
+ }
+}
+
+// Returns an expression of type Expr<_, _>. Expects interpolated variables
+// to be of type SubExpr<_, _>.
+fn quote_expr(expr: &Expr<X, X>, ctx: &Context<Label, ()>) -> TokenStream {
+ use dhall_core::ExprF::*;
+ match expr.map_ref(
+ |e| quote_subexpr(e, ctx),
+ |l, e| quote_subexpr(e, &ctx.insert(l.clone(), ())),
+ |_| unreachable!(),
+ |_| unreachable!(),
+ |l| l.clone(),
+ ) {
+ Var(V(ref s, n)) => {
+ match ctx.lookup(s, n) {
+ // Non-free variable; interpolates as itself
+ Some(()) => {
+ let s: String = s.into();
+ let var = quote! { dhall_core::V(#s.into(), #n) };
+ quote! { dhall_core::ExprF::Var(#var) }
+ }
+ // Free variable; interpolates as a rust variable
+ None => {
+ let s: String = s.into();
+ // TODO: insert appropriate shifts ?
+ let v: TokenStream = s.parse().unwrap();
+ quote! { {
+ let x: dhall_core::SubExpr<_, _> = #v.clone();
+ x.unroll()
+ } }
+ }
+ }
+ }
+ e => quote_exprf(e),
}
}
diff --git a/dhall_generator/src/dhall_type.rs b/dhall_generator/src/dhall_type.rs
index ec023bc..3b1d1c9 100644
--- a/dhall_generator/src/dhall_type.rs
+++ b/dhall_generator/src/dhall_type.rs
@@ -48,7 +48,7 @@ pub fn derive_for_struct(
})
.collect();
let record =
- crate::dhall_expr::quote_expr(dhall_core::ExprF::RecordType(fields));
+ crate::dhall_expr::quote_exprf(dhall_core::ExprF::RecordType(fields));
Ok(quote! { dhall_core::rc(#record) })
}
@@ -93,7 +93,7 @@ pub fn derive_for_enum(
.collect::<Result<_, Error>>()?;
let union =
- crate::dhall_expr::quote_expr(dhall_core::ExprF::UnionType(variants));
+ crate::dhall_expr::quote_exprf(dhall_core::ExprF::UnionType(variants));
Ok(quote! { dhall_core::rc(#union) })
}
diff --git a/dhall_generator/src/lib.rs b/dhall_generator/src/lib.rs
index d720b67..f31faa4 100644
--- a/dhall_generator/src/lib.rs
+++ b/dhall_generator/src/lib.rs
@@ -5,9 +5,20 @@ mod dhall_type;
use proc_macro::TokenStream;
+// Deprecated
#[proc_macro]
pub fn dhall_expr(input: TokenStream) -> TokenStream {
- dhall_expr::dhall_expr(input)
+ subexpr(input)
+}
+
+#[proc_macro]
+pub fn expr(input: TokenStream) -> TokenStream {
+ dhall_expr::expr(input)
+}
+
+#[proc_macro]
+pub fn subexpr(input: TokenStream) -> TokenStream {
+ dhall_expr::subexpr(input)
}
#[proc_macro_derive(Type)]