{-# LANGUAGE ScopedTypeVariables #-} {-# LANGUAGE DataKinds #-} {-# LANGUAGE KindSignatures #-} module Ivory.Language.Type where import Ivory.Language.Proxy import qualified Ivory.Language.Syntax as AST -- Ivory Types ----------------------------------------------------------------- -- | The connection between Haskell and Ivory types. class IvoryType t where ivoryType :: Proxy t -> AST.Type -- | @void@ type instance IvoryType () where ivoryType _ = AST.TyVoid -- | Lifting a variable name. class IvoryType t => IvoryVar t where wrapVar :: AST.Var -> t unwrapExpr :: t -> AST.Expr -- | Unwrapping for Ivory expressions. class IvoryVar t => IvoryExpr t where wrapExpr :: AST.Expr -> t -- Utilities ------------------------------------------------------------------- -- XXX do not export wrapVarExpr :: IvoryExpr t => AST.Var -> t wrapVarExpr = wrapExpr . AST.ExpVar -- XXX do not export typedExpr :: forall t. IvoryVar t => t -> AST.Typed AST.Expr typedExpr t = AST.Typed { AST.tType = ivoryType (Proxy :: Proxy t) , AST.tValue = unwrapExpr t } -- XXX do not export exprBinop :: IvoryExpr a => (AST.Expr -> AST.Expr -> AST.Expr) -> (a -> a -> a) exprBinop k x y = wrapExpr (k (unwrapExpr x) (unwrapExpr y)) -- XXX do not export exprUnary :: IvoryExpr a => (AST.Expr -> AST.Expr) -> (a -> a) exprUnary k x = wrapExpr (k (unwrapExpr x)) -- Proxy Type ------------------------------------------------------------------ -- | An opaque type that can never be implemented. data OpaqueType = OpaqueType instance IvoryType OpaqueType where ivoryType _ = AST.TyOpaque