aboutsummaryrefslogtreecommitdiff
path: root/Sil/Types.icl
diff options
context:
space:
mode:
authorCamil Staps2017-07-27 22:53:45 +0200
committerCamil Staps2017-07-27 22:53:45 +0200
commitbf0a7bb68485c87737677e4bbb5278b24dcb24cc (patch)
tree468c77df0e0e7e5d05047c8aec50b77d57d3b5dc /Sil/Types.icl
parentOptimise multiple pop instructions (diff)
Add tuples (see #1)
Diffstat (limited to 'Sil/Types.icl')
-rw-r--r--Sil/Types.icl35
1 files changed, 27 insertions, 8 deletions
diff --git a/Sil/Types.icl b/Sil/Types.icl
index cd9b9a4..55e1cc0 100644
--- a/Sil/Types.icl
+++ b/Sil/Types.icl
@@ -1,6 +1,7 @@
implementation module Sil.Types
-from StdFunc import const
+import StdBool
+from StdFunc import const, o
import StdList
import StdMisc
import StdOverloaded
@@ -12,22 +13,25 @@ import Control.Applicative
import Control.Monad
import Data.Error
from Data.Func import $
+import Data.Functor
import Data.Maybe
from Text import <+
from ABC.Assembler import :: BasicType(..)
import Sil.Syntax
+import Sil.Util.Printer
derive gEq Type
instance == Type where == a b = gEq{|*|} a b
instance toString Type
where
- toString TBool = "Bool"
- toString TInt = "Int"
- toString TVoid = "Void"
- toString (at --> rt) = "(" <+ at <+ " -> " <+ rt <+ ")"
+ toString TBool = "Bool"
+ toString TInt = "Int"
+ toString TVoid = "Void"
+ toString (at --> rt) = "(" <+ at <+ " -> " <+ rt <+ ")"
+ toString (TTuple _ ts) = "(" <+ printersperse ", " ts <+ ")"
instance toString TypeError
where
@@ -36,9 +40,10 @@ where
instance zero TypeSize where zero = {asize=0, bsize=0, btypes=[]}
typeSize :: Type -> TypeSize
-typeSize TVoid = zero
-typeSize TBool = {zero & bsize=1, btypes=[BT_Bool]}
-typeSize TInt = {zero & bsize=1, btypes=[BT_Int]}
+typeSize TVoid = zero
+typeSize TBool = {zero & bsize=1, btypes=[BT_Bool]}
+typeSize TInt = {zero & bsize=1, btypes=[BT_Int]}
+typeSize (TTuple _ _) = {zero & asize=1}
(+~) infixl 6 :: TypeSize TypeSize -> TypeSize
(+~) a b =
@@ -83,6 +88,20 @@ where
( top >>= \top ->
te1 >>= \te1 ->
te2 >>= \te2 -> foldM tryApply top [te1,te2])
+ type res (Tuple n es) =
+ mapM (type res) es >>= \ats -> pure (sequence ats >>= pure o TTuple n)
+ type res (Field f e)
+ | isTuple = type res e >>= \te -> pure (te >>= \te -> case te of
+ TTuple arity es -> if (0 < tupleEl && tupleEl <= arity)
+ (Ok $ es!!(tupleEl - 1))
+ (Error $ IllegalField f te)
+ _ -> Error $ IllegalField f te)
+ | otherwise = type res e >>= \te -> pure (te >>= Error o IllegalField f)
+ where
+ f` = fromString f
+
+ isTuple = length f` >= 2 && hd f` == '_' && all isDigit (tl f`)
+ tupleEl = toInt $ toString $ tl f`
tryApply :: Type Type -> MaybeError TypeError Type
tryApply ft=:(at --> rt) et