-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathParser.y
106 lines (83 loc) · 2.57 KB
/
Parser.y
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
{
{-# OPTIONS_GHC -w #-}
module Parser where
-- Author: Aleksander Balicki
-- A parser
import Lexer
import Control.Monad.State
import qualified Data.Map as Map
import AST
}
%name parse character
%tokentype { Token }
%error { parseError }
%monad { State (Int, Map.Map Condition Int) }
%token
And { (_,TkAnd) }
LParen { (_,TkLParen) }
RParen { (_,TkRParen) }
If { (_,TkIf) }
Decision { (_,TkDecision)}
Case { (_,TkCase) }
ElseIf { (_,TkElseIf) }
Int { (_,TkInt $$) }
String { (_,TkString $$)}
Equals { (_,TkEquals) }
Wildcard { (_,TkWildcard)}
Or { (_,TkOr) }
Var { (_,TkVar) }
Arm { (_,TkArm) }
%%
character :: { Character }
character: LParen rules RParen { $2 }
rules :: { [Rule] }
rules: rule rules { $1 : $2 }
| { [] }
rule :: { Rule }
rule: LParen statenumbers statement RParen { ($2, $3) }
statement :: { Term }
statement: LParen If condition statement LParen
elseifs RParen statement RParen { TmIf $3 $4 $6 $8 }
| LParen Decision newstate utterance
RParen { TmDecision $3 $4 }
| LParen Case variable LParen arms
RParen statement RParen { TmCase $3 $5 $7 }
elseifs :: { [(Condition, Term)] }
elseifs: elseif elseifs { $1 : $2 }
| { [] }
elseif :: { (Condition, Term) }
elseif: LParen ElseIf condition statement RParen { ($3, $4) }
arms :: { [(ValueSet, Term)] }
arms: arm arms { $1 : $2 }
| { [] }
arm :: { (ValueSet, Term) }
arm: LParen Arm valueset statement RParen { ($3, $4) }
condition :: { Condition }
condition: LParen Equals variable Int RParen {% cachedCondition (TmEquals $3 $4 0) }
| LParen And conditions RParen {% cachedCondition (TmAnd $3 0) }
| LParen Or conditions RParen {% cachedCondition (TmOr $3 0) }
conditions ::{ [Condition] }
conditions: condition conditions { $1 : $2 }
| { [] }
variable :: { Variable }
variable: LParen Var String RParen { TmVar $3 }
statenumbers :: { [StateNumber] }
statenumbers: statenumber statenumbers { $1 : $2 }
| { [] }
statenumber :: { StateNumber }
statenumber: Int { $1 }
newstate :: { NewState }
newstate: Int { TmState $1 }
| Wildcard { TmCurrent }
utterance :: { Utterance }
utterance: String { $1 }
values :: { [Integer] }
values: Int values { $1 : $2 }
| { [] }
valueset :: { ValueSet }
valueset: LParen values RParen { $2 }
{
parseError :: [Token] -> a
parseError (((line,col),t):xs) = error $ "Parse error at token " ++ show t ++", line " ++ (show line) ++ ", column " ++ (show col)
parseError [] = error "Parse error at the end"
}