]> gitweb.ps.run Git - toc/blob - Toc.g4
type modifiers, parenthesized expressions, chained access expressions
[toc] / Toc.g4
1 grammar Toc;\r
2 \r
3 prog: (decl)+ EOF;\r
4 \r
5 decl: varDecl ';'\r
6     | funcDecl\r
7     | structDecl\r
8     ;\r
9 \r
10 varDecl:  'var' var;\r
11 var:  varName (':' type) ('=' expr)?;\r
12 varInit:  varName (':' type) ('=' expr);\r
13 \r
14 type: typeName (typeModifier)*;\r
15 typeModifier: '*' | ('[' (INT_LIT)? ']');\r
16 \r
17 \r
18 funcDecl: 'func' func;\r
19 func: funcName '(' parameter ')' (':' type) body;\r
20 parameter: (var (',' var)*)?;\r
21 \r
22 body: '{' stmt* '}';\r
23 \r
24 \r
25 structDecl: 'struct' structName '{' structMember* '}';\r
26 structMember: structVar | structMethod;\r
27 structVar: var ';';\r
28 structMethod: func;\r
29 \r
30 \r
31 stmt: varDecl ';'\r
32     | ifStmt\r
33     | switchStmt\r
34     | forStmt\r
35     | whileStmt\r
36     | assignStmt ';'\r
37     | returnStmt ';'\r
38     | expr ';';\r
39 \r
40 ifStmt: 'if' expr body elseIfStmt* elseStmt?;\r
41 elseIfStmt: 'else' 'if' expr body;\r
42 elseStmt: 'else' body;\r
43 \r
44 switchStmt: 'switch' identifierExpr switchBody;\r
45 switchBody: '{' switchCase* '}';\r
46 switchCase: 'case' expr body;\r
47 \r
48 forStmt: 'for' (varInit | assignStmt) ',' expr ',' expr body;\r
49 \r
50 whileStmt: 'while' expr body;\r
51 \r
52 assignStmt: identifierExpr '=' expr;\r
53 \r
54 returnStmt: 'return' expr;\r
55 \r
56 expr: funcExpr\r
57     | litExpr\r
58     | identifierExpr\r
59     | parenExpr\r
60     | accessExpr\r
61     | opExpr;\r
62 \r
63 /* op */\r
64 nonOpExpr: funcExpr\r
65          | litExpr\r
66          | identifierExpr\r
67          | parenExpr\r
68          | accessExpr;\r
69 \r
70 /* lit access op */\r
71 nonAccessExpr: funcExpr\r
72              | identifierExpr\r
73              | parenExpr;\r
74 \r
75 funcExpr: funcName '(' (expr (',' expr)*)? ')';\r
76 \r
77 opExpr: binaryOp | prefixOp | postfixOp | ternaryOp;\r
78 binaryOp: nonOpExpr binary_op nonOpExpr (binary_op nonOpExpr)*;\r
79 prefixOp: prefix_op nonOpExpr;\r
80 postfixOp: nonOpExpr postfix_op;\r
81 ternaryOp: nonOpExpr '?' expr ':' expr;\r
82 \r
83 identifierExpr: varName;\r
84 \r
85 litExpr: INT_LIT | DECIMAL_LIT | STRING_LIT | BOOL_LIT;\r
86 \r
87 accessExpr: nonAccessExpr (accessSubExpr)+;\r
88 accessSubExpr: accessMember | accessBrackets;\r
89 accessMember: ('.' | '->') identifierExpr;\r
90 accessBrackets: '[' expr ']';\r
91 \r
92 parenExpr: '(' expr ')';\r
93 \r
94 funcName: NAME;\r
95 varName: NAME;\r
96 typeName: NAME;\r
97 structName: NAME;\r
98 \r
99 \r
100 postfix_op:\r
101     '++' | '--';\r
102 prefix_op:\r
103     '+' | '-' | '!' | '~' | '&' | '*' | postfix_op;\r
104 binary_op:\r
105     '+' | '-' | '*' | '/' | '%' | '&' | '<' | '|' | '^' | '>' |\r
106     '==' | '!=' | '<=' | '>=' | '<'  | '>' |\r
107     '<<' | '>>' | '||' | '&&' | '&=' | '|=' | '^=' |\r
108     '<<=' | '>>=' | '+=' | '-=' | '*=' | '/=' | '%=';\r
109 \r
110 INT_LIT: ('+' | '-')? [0-9]+;\r
111 DECIMAL_LIT: ('+' | '-')* [0-9]+ '.' [0-9]+;\r
112 STRING_LIT: '"' [^"]* '"';\r
113 BOOL_LIT: 'true' | 'false';\r
114 \r
115 NAME: ([a-z] | [A-Z] | [0-9])+;\r
116 WS: [ \t\r\n]+ -> skip;\r
117 NEWLINE: [\r\n]+;\r