1
%{
2
#include "parser.h"
3
%}
4
5
%parse-param {ast_t *ast}
6
%error-verbose
7
8
%union {
9
ast_comment_t *comment;
10
ast_token_t *token;
11
ast_expr_t *expr;
12
13
ast_stmt_t *stmt;
14
}
15
16
%token END_OF_FILE 0 "$end"
17
18
%token NL
19
20
%token <token> TOKEN
21
%token <expr> IMM
22
%token <comment> COMMENT
23
24
%type <stmt> line stmt
25
%type <expr> expr exprlist opt_exprlist
26
27
%left '+' '-'
28
%left '*' '/'
29
30
%left '(' ')'
31
32
%%
33
34
input: /* empty */
35
| input line { if ($2) { ast_append_stmt(ast, $2); } }
36
;
37
38
line_separator: NL
39
| ':'
40
;
41
42
line: line_separator { $$ = 0; }
43
| stmt line_separator { $$ = $1; }
44
| stmt END_OF_FILE { $$ = $1; }
45
;
46
47
stmt: TOKEN opt_exprlist { $$ = ast_stmt_alloc(STMT_CALL); $$->call.target = $1; $$->call.args = $2; }
48
| COMMENT { $$ = ast_stmt_alloc(STMT_COMMENT); $$->comment = $1; }
49
;
50
51
exprlist: expr { $$ = $1; }
52
| expr ',' exprlist { $$ = $1; $1->next = $3; $1->nexttype = ','; }
53
| expr ';' exprlist { $$ = $1; $1->next = $3; $1->nexttype = ';'; }
54
| expr exprlist { $$ = $1; $1->next = $2; $1->nexttype = ';'; }
55
;
56
57
opt_exprlist: /* empty */ { $$ = 0; }
58
| exprlist { $$ = $1; }
59
;
60
61
expr: IMM { $$ = $1; }
62
| '(' expr ')' { $$ = $2; }
63
| expr '+' expr { $$ = ast_binary_alloc('+', $1, $3); }
64
| expr '-' expr { $$ = ast_binary_alloc('-', $1, $3); }
65
| expr '*' expr { $$ = ast_binary_alloc('*', $1, $3); }
66
| expr '/' expr { $$ = ast_binary_alloc('/', $1, $3); }
67
;
68
69
/* vim: set sw=4 et: */
70