Revision ae9f5b95ebf7b36577861434e2099b638540d730 authored by Anish Tondwalkar on 20 October 2019, 06:45:47 UTC, committed by Anish Tondwalkar on 20 October 2019, 06:45:47 UTC
1 parent eba2590
Raw File
testParser.hs
{-# LANGUAGE OverloadedStrings #-}

module Main where

import Language.Fixpoint.Types (showFix)
import Language.Fixpoint.Parse
import Test.Tasty
import Test.Tasty.HUnit
import Data.List (intercalate)

main :: IO ()
main = defaultMain $ parserTests

parserTests :: TestTree
parserTests =
  testGroup "Tests"
    [ testSortP
    , testFunAppP
    , testExpr0P
    , testPredP
    , testDeclP
    ]

-- ---------------------------------------------------------------------
{-

sort = '(' sort ')'
     | 'func' funcSort
     | '[' sort ']'
     | bvsort
     | fTyCon
     | tVar

sorts = '[' sortslist ']'

sortslist = sort
          | sort `;` sortslist

funcSort = '(' int `,` sorts ')'

     e.g.(func(1, [int; @(0)]))

bvsort = '(' 'BitVec' 'Size32' ')'
       | '(' 'BitVec' 'Size64' ')'

fTyCon = 'int' | 'Integer' | 'Int' | 'real' | 'num' | 'Str'
       | SYMBOL

SYMBOL = upper case char or _, followed by many of '%' '#' '$' '\'

tVar = '@' varSort
     | LOWERID

varSort = '(' INT ')'
-}

testSortP :: TestTree
testSortP =
  testGroup "SortP"
    [ testCase "FAbs" $
        show (doParse' sortP "test" "(func(1, [int; @(0)]))") @?= "FAbs 0 (FFunc FInt (FVar 0))"

    , testCase "(FAbs)" $
        show (doParse' sortP "test" "((func(1, [int; @(0)])))") @?= "FAbs 0 (FFunc FInt (FVar 0))"

    , testCase "FApp FInt" $
        show (doParse' sortP "test" "[int]") @?=
              "FApp (FTC (TC \"[]\" (dummyLoc) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = False}))) FInt"

    , testCase "bv32" $
        show (doParse' sortP "test" "BitVec Size32") @?=
              "FApp (FTC (TC \"BitVec\" defined from: \"test\" (line 1, column 1) to: \"test\" (line 1, column 8) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = False}))) (FTC (TC \"Size32\" defined from: \"test\" (line 1, column 8) to: \"test\" (line 1, column 14) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = False})))"

    , testCase "bv64" $
        show (doParse' sortP "test" "BitVec Size64") @?=
              "FApp (FTC (TC \"BitVec\" defined from: \"test\" (line 1, column 1) to: \"test\" (line 1, column 8) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = False}))) (FTC (TC \"Size64\" defined from: \"test\" (line 1, column 8) to: \"test\" (line 1, column 14) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = False})))"

    , testCase "FInt int" $
        show (doParse' sortP "test" "int") @?= "FInt"

    , testCase "FInt Integer" $
        show (doParse' sortP "test" "Integer") @?= "FInt"

    , testCase "FInt Int" $
        show (doParse' sortP "test" "Int") @?= "FInt"

    , testCase "FReal real" $
        show (doParse' sortP "test" "real") @?= "FReal"

    , testCase "FNum num" $
        show (doParse' sortP "test" "num") @?= "FNum"

    , testCase "FStr" $
        show (doParse' sortP "test" "Str") @?=
             "FTC (TC \"Str\" (dummyLoc) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = True}))"

    , testCase "SYMBOL" $
        show (doParse' sortP "test" "F#y") @?=
             "FTC (TC \"F#y\" defined from: \"test\" (line 1, column 1) to: \"test\" (line 1, column 4) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = False}))"

    , testCase "FVar 3" $
        show (doParse' sortP "test" "@(3)") @?= "FVar 3"

    , testCase "FObj " $
        show (doParse' sortP "test" "foo") @?= "FObj \"foo\""

    , testCase "FObj " $
        show (doParse' sortP "test" "_foo") @?= "FObj \"_foo\""

    , testCase "Coerce0" $
        show (doParse' predP "test" "v = (coerce (a ~ int) (f x))")
          @?= "PAtom Eq (EVar \"v\") (ECoerc (FObj \"a\") FInt (EApp (EVar \"f\") (EVar \"x\")))"
    ]

-- ---------------------------------------------------------------------
{-

funApp = lit
       | exprFunSpaces
       | expFunSemis
       | expFunCommas
       | simpleApp

lit = 'lit' stringLiteral sort

exprFunSpaces =

exprFunSemis =

exprFunCommas =

simpleApp =
-}
testFunAppP :: TestTree
testFunAppP =
  testGroup "FunAppP"
    [ testCase "ECon (litP)" $
        show (doParse' funAppP "test" "lit \"#x00000008\" (BitVec  Size32)") @?=
          "ECon (L \"#x00000008\" (FApp (FTC (TC \"BitVec\" defined from: \"test\" (line 1, column 19) to: \"test\" (line 1, column 27) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = False}))) (FTC (TC \"Size32\" defined from: \"test\" (line 1, column 27) to: \"test\" (line 1, column 33) (TCInfo {tc_isNum = False, tc_isReal = False, tc_isString = False})))))"

    , testCase "ECon (exprFunSpacesP)" $
        show (doParse' funAppP "test" "fooBar baz qux") @?= "EApp (EApp (EVar \"fooBar\") (EVar \"baz\")) (EVar \"qux\")"

    , testCase "ECon (exprFunCommasP)" $
        show (doParse' funAppP "test" "fooBar (baz, qux)") @?= "EApp (EVar \"fooBar\") (EApp (EApp (EVar \"(,)\") (EVar \"baz\")) (EVar \"qux\"))"

    , testCase "ECon (exprFunSemisP)" $
        show (doParse' funAppP "test" "fooBar ([baz; qux])") @?= "EApp (EApp (EVar \"fooBar\") (EVar \"baz\")) (EVar \"qux\")"

    , testCase "ECon (simpleAppP)" $
        show (doParse' funAppP "test" "fooBar (baz + 1)") @?= "EApp (EVar \"fooBar\") (EBin Plus (EVar \"baz\") (ECon (I 1)))"
    ]

-- ---------------------------------------------------------------------
{-
expr0 = fastIf
      | symconst
      | constant
      | '_|_'
      | lam
      | '(' expr ')'
      | '(' exprCast ')'
      | symChars

-}
testExpr0P :: TestTree
testExpr0P =
  testGroup "expr0P"
    [ testCase "EIte" $
        show (doParse' expr0P "test" "if true then x else y") @?= "EIte (PAnd []) (EVar \"x\") (EVar \"y\")"

    , testCase "ESym SL" $
        show (doParse' expr0P "test" "\"foo\" ") @?= "ESym (SL \"foo\")"

    , testCase "ECon R" $
        show (doParse' expr0P "test" "0.0") @?= "ECon (R 0.0)"

    , testCase "ECon I" $
        show (doParse' expr0P "test" "0") @?= "ECon (I 0)"

    , testCase "ECon I" $
        show (doParse' expr0P "test" "0") @?= "ECon (I 0)"

    , testCase "EBot / POr []" $
        show (doParse' expr0P "test" "_|_") @?= "POr []" -- pattern for "EBot"

    , testCase "ELam" $
        show (doParse' expr0P "test" "\\ foo : Int -> true") @?= "ELam (\"foo\",FInt) (PAnd [])"

    , testCase "Expr" $
        show (doParse' expr0P "test" "(1)") @?= "ECon (I 1)"

    , testCase "ECst dcolon" $
        show (doParse' expr0P "test" "(1 :: Int)") @?= "ECst (ECon (I 1)) FInt"

    , testCase "ECst colon" $
        show (doParse' expr0P "test" "(1 : Int)") @?= "ECst (ECon (I 1)) FInt"

    , testCase "charsExpr EVar" $
        show (doParse' expr0P "test" "foo") @?= "EVar \"foo\""

    , testCase "charsExpr ECon" $
        show (doParse' expr0P "test" "1") @?= "ECon (I 1)"
    ]

-- ---------------------------------------------------------------------
{-

pred = expressionParse (prefixOp++infixOp) pred0

prefixOp = '~' | 'not'

infixOp  = '&&' | '||' | '=>' | '==>' | '<=>'

-- terms are pred0
pred0 = 'true' | 'false'
      | '??'
      | kvarPred
      | fastIfP
      | predr
      | '(' pred ')'
      | '?' expr
      | funApp
      | symbol
      | '&&' preds
      | '||' preds

kvarPred = kvar substs

kvar = '$' symbol

substs = {- empty -}
       | subst substs

subst = '[' symbol ':=' expr ']'

preds = '[' predslist ']'

predslist = pred
          | pred `;` predslist

fastIf = 'if' pred 'then' pred 'else' pred

predr = expr brel expr

brelP = '==' | '=' | '~~' | '!=' | '/=' | '!~' | '<' | '<=' | '>' | '>='

-}

testPredP :: TestTree
testPredP =
  testGroup "predP"
    [ testCase "PTrue" $
        show (doParse' predP "test" "true") @?= "PAnd []" -- pattern for PTrue

    , testCase "PFalse" $
        show (doParse' predP "test" "false") @?= "POr []" -- pattern for PFalse

   --     , testCase "PGrad / ??" $
   --       show (doParse' predP "test" "??") @?= "PGrad $\"\\\"test\\\" (line 1, column 3)\"  (PAnd [])"
   --   "PGrad $\"\\\"test\\\" (line 1, column 3)\"  (GradInfo {gsrc = SS {sp_start = \"test\" (line 1, column 3), sp_stop = \"test\" (line 1, column 3)}, gused = Nothing}) (PAnd [])"

    , testCase "kvarPred empty" $
        show (doParse' predP "test" "$foo") @?= "PKVar $\"foo\" "

    , testCase "kvarPred one" $
        show (doParse' predP "test" "$foo  [x := 1]") @?= "PKVar $\"foo\" [x:=1]"

    , testCase "kvarPred two" $
        show (doParse' predP "test" "$foo  [x := 1] [ y := true ]") @?= "PKVar $\"foo\" [x:=1][y:=true]"

    , testCase "fastIf" $
        show (doParse' predP "test" "if true then true else false" ) @?=
          -- note conversion
          "PAnd [PImp (PAnd []) (PAnd []),PImp (PNot (PAnd [])) (POr [])]"

    , testCase "brel" $
        show (doParse' predP "test" "1 == 2") @?= "PAtom Eq (ECon (I 1)) (ECon (I 2))"

    , testCase "parens pred" $
        show (doParse' predP "test" "((1 == 2))") @?= "PAtom Eq (ECon (I 1)) (ECon (I 2))"

    , testCase "? expr" $
        show (doParse' predP "test" "? (1+2)") @?= "EBin Plus (ECon (I 1)) (ECon (I 2))"

    , testCase "funApp 1" $
        show (doParse' predP "test" "f a b") @?= "EApp (EApp (EVar \"f\") (EVar \"a\")) (EVar \"b\")"

    , testCase "funApp 2" $
        show (doParse' predP "test" "f (a, b)") @?= "EApp (EVar \"f\") (EApp (EApp (EVar \"(,)\") (EVar \"a\")) (EVar \"b\"))"

    , testCase "funApp 3" $
        show (doParse' predP "test" "f ([a; b])") @?= "EApp (EApp (EVar \"f\") (EVar \"a\")) (EVar \"b\")"

    , testCase "symbol" $
        show (doParse' predP "test" "f") @?= "EVar \"f\""

    , testCase "&& 0" $
        show (doParse' predP "test" "&& []") @?= "PAnd []"

    , testCase "&& 1" $
        show (doParse' predP "test" "&& [x]") @?= "PAnd [EVar \"x\"]"

    , testCase "&& 2" $
        show (doParse' predP "test" "&& [x;y]") @?= "PAnd [EVar \"x\",EVar \"y\"]"

    , testCase "|| 0" $
        show (doParse' predP "test" "|| []") @?= "POr []"

    , testCase "|| 1" $
        show (doParse' predP "test" "|| [x]") @?= "POr [EVar \"x\"]"

    , testCase "|| 2" $
        show (doParse' predP "test" "|| [x;y]") @?= "POr [EVar \"x\",EVar \"y\"]"
    ]


{-

data Vec 1 = [
    Nil {}
  | Cons { vHead : @(0), vTail : Vec @(0)}
  ]

-}

testDeclP :: TestTree
testDeclP = testGroup "dataDeclP"
  [ mkT "fld0"  dataFieldP fld0
  , mkT "fld1"  dataFieldP fld1
  , mkT "fld2"  dataFieldP fld2
  , mkT "ctor0" dataCtorP  ctor0
  , mkT "ctor1" dataCtorP  ctor1
  , mkT "decl0" dataDeclP decl0
  ]
  where
    mkT name p t = testCase name $ showFix (doParse' p "test" t) @?= t
    fld0    = "vHead : int"
    fld1    = "vHead : @(0)"
    fld2    = "vTail : (Vec @(0))"
    ctor0   = "nil {}"
    ctor1   = "cons {vHead : @(0), vTail : (Vec @(0))}"
    decl0   = intercalate "\n"
                [ "Vec 1 = ["
                , "  | nil {}"
                , "  | cons {vHead : @(0), vTail : Vec}"
                , "]"
                ]
back to top