Types.hs 2.2 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677
  1. module Gidl.Types
  2. ( module Gidl.Types.AST
  3. , module Gidl.Types.Base
  4. , TypeDescr
  5. , TypeRepr(..)
  6. , lookupTypeName
  7. , insertType
  8. , typeLeaves
  9. , typeDescrToRepr
  10. , sizeOf
  11. , voidTypeRepr
  12. ) where
  13. import Data.List (nub)
  14. import Data.Maybe (fromJust)
  15. import Gidl.Types.AST
  16. import Gidl.Types.Base
  17. lookupTypeName :: TypeName -> TypeEnv -> Maybe TypeDescr
  18. lookupTypeName tn te =
  19. case aux te of
  20. Just a -> Just a
  21. Nothing -> case aux baseTypeEnv of
  22. Just a -> Just a
  23. Nothing -> Nothing
  24. where
  25. aux (TypeEnv e) = lookup tn e
  26. insertType :: TypeName -> TypeDescr -> TypeEnv -> TypeEnv
  27. insertType tn t e@(TypeEnv te) = case lookupTypeName tn e of
  28. Nothing -> TypeEnv ((tn,t):te)
  29. Just _ -> error ("insertType invariant broken: type " ++ tn ++ " already exists")
  30. typeLeaves :: (Eq t) => Type t -> [t]
  31. typeLeaves (StructType (Struct s)) = nub (map snd s)
  32. typeLeaves (NewtypeType (Newtype tn)) = [tn]
  33. typeLeaves (EnumType _) = []
  34. typeLeaves (AtomType _) = []
  35. typeLeaves VoidType = []
  36. type TypeDescr = Type TypeName
  37. data TypeRepr = TypeRepr TypeName (Type TypeRepr)
  38. deriving (Eq, Show)
  39. voidTypeRepr :: TypeRepr
  40. voidTypeRepr = TypeRepr "void" VoidType
  41. -- invariant: TypeName exists in a well-formed TypeEnv
  42. typeDescrToRepr :: TypeName -> TypeEnv -> TypeRepr
  43. typeDescrToRepr tn te = TypeRepr tn tr
  44. where
  45. tr = case fromJust $ lookupTypeName tn te of
  46. EnumType e -> EnumType e
  47. AtomType a -> AtomType a
  48. NewtypeType (Newtype ntn) ->
  49. NewtypeType (Newtype (typeDescrToRepr ntn te))
  50. StructType (Struct s) ->
  51. StructType (Struct [(i, typeDescrToRepr stn te) | (i, stn) <- s])
  52. VoidType -> VoidType
  53. sizeOf :: TypeRepr -> Integer
  54. sizeOf (TypeRepr _ (StructType (Struct s))) = sum [ sizeOf tr | (_, tr) <- s ]
  55. sizeOf (TypeRepr _ (NewtypeType (Newtype tr))) = sizeOf tr
  56. sizeOf (TypeRepr _ (EnumType (EnumT bs _))) = bitsSize bs
  57. sizeOf (TypeRepr _ (AtomType (AtomInt bs))) = bitsSize bs
  58. sizeOf (TypeRepr _ (AtomType (AtomWord bs))) = bitsSize bs
  59. sizeOf (TypeRepr _ (AtomType AtomFloat)) = 4
  60. sizeOf (TypeRepr _ (AtomType AtomDouble)) = 8
  61. sizeOf (TypeRepr _ VoidType) = 0
  62. bitsSize :: Bits -> Integer
  63. bitsSize Bits8 = 1
  64. bitsSize Bits16 = 2
  65. bitsSize Bits32 = 4
  66. bitsSize Bits64 = 8