2024-07-26 12:22:07 +02:00
|
|
|
module Language.Elna.SymbolTable
|
2024-09-08 02:08:13 +02:00
|
|
|
( SymbolTable
|
|
|
|
, empty
|
|
|
|
{-, Info(..)
|
2024-07-26 12:22:07 +02:00
|
|
|
, ParameterInfo(..)
|
2024-08-05 22:56:35 +02:00
|
|
|
, builtInSymbolTable
|
2024-07-29 07:26:47 +02:00
|
|
|
, enter
|
2024-08-04 12:23:19 +02:00
|
|
|
, fromList
|
2024-07-29 07:26:47 +02:00
|
|
|
, lookup
|
2024-09-08 02:08:13 +02:00
|
|
|
, member -}
|
2024-07-26 12:22:07 +02:00
|
|
|
) where
|
|
|
|
|
2024-09-08 02:08:13 +02:00
|
|
|
data SymbolTable = SymbolTable -- (HashMap Identifier Info)
|
|
|
|
deriving (Eq, Show)
|
|
|
|
|
|
|
|
empty :: SymbolTable
|
|
|
|
empty = SymbolTable -- HashMap.empty
|
|
|
|
|
|
|
|
{-
|
2024-07-26 12:22:07 +02:00
|
|
|
import Data.HashMap.Strict (HashMap)
|
2024-07-29 07:26:47 +02:00
|
|
|
import qualified Data.HashMap.Strict as HashMap
|
2024-08-05 22:56:35 +02:00
|
|
|
import Data.List (sort)
|
|
|
|
import Data.List.NonEmpty (NonEmpty)
|
|
|
|
import qualified Data.List.NonEmpty as NonEmpty
|
2024-07-26 12:22:07 +02:00
|
|
|
import Data.Vector (Vector)
|
2024-07-29 07:26:47 +02:00
|
|
|
import Language.Elna.Location (Identifier(..))
|
|
|
|
import Language.Elna.Types (Type(..), intType, booleanType)
|
|
|
|
import Prelude hiding (lookup)
|
2024-07-26 12:22:07 +02:00
|
|
|
|
2024-07-29 07:26:47 +02:00
|
|
|
instance Semigroup SymbolTable
|
|
|
|
where
|
|
|
|
(SymbolTable lhs) <> (SymbolTable rhs) = SymbolTable $ rhs <> lhs
|
2024-07-26 12:22:07 +02:00
|
|
|
|
2024-07-29 07:26:47 +02:00
|
|
|
instance Monoid SymbolTable
|
2024-07-26 12:22:07 +02:00
|
|
|
where
|
2024-08-05 22:56:35 +02:00
|
|
|
mempty = empty
|
2024-07-26 12:22:07 +02:00
|
|
|
|
2024-08-04 12:23:19 +02:00
|
|
|
builtInSymbolTable :: SymbolTable
|
|
|
|
builtInSymbolTable = SymbolTable $ HashMap.fromList
|
2024-07-29 07:26:47 +02:00
|
|
|
[ ("boolean", TypeInfo booleanType)
|
|
|
|
, ("int", TypeInfo intType)
|
|
|
|
]
|
2024-07-26 12:22:07 +02:00
|
|
|
|
2024-08-05 22:56:35 +02:00
|
|
|
enter :: Identifier -> Info -> SymbolTable -> Maybe SymbolTable
|
|
|
|
enter identifier info table@(SymbolTable hashTable)
|
|
|
|
| member identifier table = Nothing
|
|
|
|
| otherwise = Just
|
|
|
|
$ SymbolTable
|
|
|
|
$ HashMap.insert identifier info hashTable
|
2024-07-26 12:22:07 +02:00
|
|
|
|
2024-07-29 07:26:47 +02:00
|
|
|
lookup :: Identifier -> SymbolTable -> Maybe Info
|
|
|
|
lookup identifier (SymbolTable table) = HashMap.lookup identifier table
|
2024-07-26 12:22:07 +02:00
|
|
|
|
2024-08-05 22:56:35 +02:00
|
|
|
member :: Identifier -> SymbolTable -> Bool
|
|
|
|
member identifier (SymbolTable table) = HashMap.member identifier table
|
|
|
|
|
|
|
|
fromList :: [(Identifier, Info)] -> Either (NonEmpty Identifier) SymbolTable
|
|
|
|
fromList elements
|
|
|
|
| Just identifierDuplicates' <- identifierDuplicates =
|
|
|
|
Left identifierDuplicates'
|
|
|
|
| otherwise = Right $ SymbolTable $ HashMap.fromList elements
|
|
|
|
where
|
|
|
|
identifierDuplicates = NonEmpty.nonEmpty
|
|
|
|
$ fmap NonEmpty.head
|
|
|
|
$ filter ((> 1) . NonEmpty.length)
|
|
|
|
$ NonEmpty.group . sort
|
|
|
|
$ fst <$> elements
|
2024-08-04 12:23:19 +02:00
|
|
|
|
2024-07-26 12:22:07 +02:00
|
|
|
data ParameterInfo = ParameterInfo
|
|
|
|
{ name :: Identifier
|
|
|
|
, type' :: Type
|
|
|
|
, isReferenceParameter :: Bool
|
|
|
|
} deriving (Eq, Show)
|
|
|
|
|
|
|
|
data Info
|
|
|
|
= TypeInfo Type
|
2024-08-12 00:50:36 +02:00
|
|
|
| VariableInfo Bool Type
|
2024-07-26 12:22:07 +02:00
|
|
|
| ProcedureInfo SymbolTable (Vector ParameterInfo)
|
|
|
|
deriving (Eq, Show)
|
2024-09-08 02:08:13 +02:00
|
|
|
-}
|