aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorYann Herklotz Grave <git@yannherklotzgrave.com>2019-02-13 19:53:30 +0000
committerYann Herklotz Grave <git@yannherklotzgrave.com>2019-02-13 19:53:30 +0000
commit7378b86829ce79f49b947a0744cbb6d8546a65aa (patch)
treeffee0315ebbc797a30b1b6dd0f07fbdabb84bbe8 /src
parentf47c9f93babddd2b238cdef64ca44fecc3d314e1 (diff)
downloadverismith-7378b86829ce79f49b947a0744cbb6d8546a65aa.tar.gz
verismith-7378b86829ce79f49b947a0744cbb6d8546a65aa.zip
Add expression to parser
Diffstat (limited to 'src')
-rw-r--r--src/VeriFuzz/Parser.hs115
1 files changed, 111 insertions, 4 deletions
diff --git a/src/VeriFuzz/Parser.hs b/src/VeriFuzz/Parser.hs
index fd56027..4b2d076 100644
--- a/src/VeriFuzz/Parser.hs
+++ b/src/VeriFuzz/Parser.hs
@@ -13,13 +13,120 @@ whole Verilog syntax, as the AST does not support it either.
module VeriFuzz.Parser where
+import Control.Applicative ((<|>))
import Data.Attoparsec.Text
+import Data.Functor (($>))
import Data.Text (Text)
import qualified Data.Text as T
import VeriFuzz.AST
+import VeriFuzz.CodeGen
-parseDescription :: Text -> Parser Description
-parseDescription = undefined
+commaSep :: Parser a -> Parser [a]
+commaSep f = sepBy f (skipSpace *> char ',' *> skipSpace)
-parseVerilogSrc :: Text -> Parser VerilogSrc
-parseVerilogSrc t = VerilogSrc <$> many1 (parseDescription t)
+aroundList :: Parser a -> Parser b -> Parser c -> Parser [c]
+aroundList a b c = do
+ l <- a *> skipSpace *> commaSep c
+ _ <- b
+ return l
+
+parseBinOp :: Parser BinaryOperator
+parseBinOp =
+ "+" $> BinPlus
+ <|> "-" $> BinMinus
+ <|> "*" $> BinTimes
+ <|> "/" $> BinDiv
+ <|> "%" $> BinMod
+ <|> "==" $> BinEq
+ <|> "!=" $> BinNEq
+ <|> "===" $> BinCEq
+ <|> "!==" $> BinCNEq
+ <|> "&&" $> BinLAnd
+ <|> "||" $> BinLOr
+ <|> "<" $> BinLT
+ <|> "<=" $> BinLEq
+ <|> ">" $> BinGT
+ <|> ">=" $> BinGEq
+ <|> "&" $> BinAnd
+ <|> "|" $> BinOr
+ <|> "^" $> BinXor
+ <|> "^~" $> BinXNor
+ <|> "~^" $> BinXNorInv
+ <|> "**" $> BinPower
+ <|> "<<" $> BinLSL
+ <|> ">>" $> BinLSR
+ <|> "<<<" $> BinASL
+ <|> ">>>" $> BinASR
+
+parseUnOp :: Parser UnaryOperator
+parseUnOp =
+ "+" $> UnPlus
+ <|> "-" $> UnMinus
+ <|> "!" $> UnLNot
+ <|> "~" $> UnNot
+ <|> "&" $> UnAnd
+ <|> "~&" $> UnNand
+ <|> "|" $> UnOr
+ <|> "~|" $> UnNor
+ <|> "^" $> UnXor
+ <|> "~^" $> UnNxor
+ <|> "^~" $> UnNxorInv
+
+parseExpr :: Parser Expr
+parseExpr = cond <|> binop <|> unop <|> conc <|> brack <|> var <|> num
+ where
+ var = Id . Identifier . T.pack <$> many1 letter
+ num = Number 32 <$> decimal
+ binop = do
+ lhs <- var <|> num
+ bo <- skipSpace *> parseBinOp
+ skipSpace
+ BinOp lhs bo <$> parseExpr
+ brack = do
+ expr <- "(" *> skipSpace *> parseExpr
+ skipSpace *> ")" *> skipSpace
+ return expr
+ cond = do
+ expr1 <- parseExpr
+ skipSpace *> "?" *> skipSpace
+ expr2 <- parseExpr
+ skipSpace *> ":" *> skipSpace
+ expr3 <- parseExpr
+ skipSpace
+ return $ Cond expr1 expr2 expr3
+ conc = Concat <$> aroundList "{" "}" parseExpr
+ unop = do
+ uo <- parseUnOp
+ skipSpace
+ UnOp uo <$> parseExpr
+
+parseContAssign :: Parser ContAssign
+parseContAssign = do
+ var <- Identifier . T.pack <$> (skipSpace *> "assign" *> skipSpace *> many1 letter)
+ expr <- skipSpace *> "=" *> skipSpace *> parseExpr
+ _ <- skipSpace *> ";"
+ return $ ContAssign var expr
+
+parseModItem :: Parser [ModItem]
+parseModItem = fmap ModCA <$> many1 parseContAssign
+
+parseModList :: Parser [Identifier]
+parseModList = list <|> skipSpace $> []
+ where
+ list = fmap (Identifier . T.pack)
+ <$> aroundList "(" ")" (many1 letter)
+
+parseModDecl :: Parser ModDecl
+parseModDecl = do
+ name <- Identifier . T.pack <$> ("module" *> skipSpace *> many1 letter)
+ modL <- fmap (Port Wire 1) <$> (skipSpace *> parseModList)
+ _ <- skipSpace *> ";"
+ modItem <- parseModItem <|> skipSpace $> []
+ _ <- skipSpace *> "endmodule"
+ return $ ModDecl name [Port Wire 1 "y"] modL modItem
+
+parseDescription :: Parser Description
+parseDescription = Description <$> (skipSpace *> parseModDecl)
+
+parseVerilogSrc :: Parser VerilogSrc
+parseVerilogSrc = VerilogSrc <$> many1 parseDescription