diff options
| author | ruki <[email protected]> | 2019-06-15 09:19:06 +0800 |
|---|---|---|
| committer | ruki <[email protected]> | 2019-06-15 09:19:06 +0800 |
| commit | 115665bd7ad421d448b7dda421303096a677dd72 (patch) | |
| tree | e10ec94c419814c6822cf6f051f98ed337bcbd53 /tests/projects | |
| parent | 42ddca8c330acd5928a553fbd562f3a3d2a4700b (diff) | |
add lex/yacc test project
Diffstat (limited to 'tests/projects')
| -rw-r--r-- | tests/projects/lex_yacc/src/calc.l | 27 | ||||
| -rw-r--r-- | tests/projects/lex_yacc/src/calc.y | 81 | ||||
| -rw-r--r-- | tests/projects/lex_yacc/xmake.lua | 7 |
3 files changed, 115 insertions, 0 deletions
diff --git a/tests/projects/lex_yacc/src/calc.l b/tests/projects/lex_yacc/src/calc.l new file mode 100644 index 000000000..37d44dd27 --- /dev/null +++ b/tests/projects/lex_yacc/src/calc.l @@ -0,0 +1,27 @@ +%option noyywrap + +%{ +#include <stdio.h> + +#define YY_DECL int yylex() + +#include "calc.tab.h" + +%} + +%% + +[ \t] ; // ignore all whitespace +[0-9]+\.[0-9]+ {yylval.fval = atof(yytext); return T_FLOAT;} +[0-9]+ {yylval.ival = atoi(yytext); return T_INT;} +\n {return T_NEWLINE;} +"+" {return T_PLUS;} +"-" {return T_MINUS;} +"*" {return T_MULTIPLY;} +"/" {return T_DIVIDE;} +"(" {return T_LEFT;} +")" {return T_RIGHT;} +"exit" {return T_QUIT;} +"quit" {return T_QUIT;} + +%% diff --git a/tests/projects/lex_yacc/src/calc.y b/tests/projects/lex_yacc/src/calc.y new file mode 100644 index 000000000..d7af910dd --- /dev/null +++ b/tests/projects/lex_yacc/src/calc.y @@ -0,0 +1,81 @@ +%{ + +#include <stdio.h> +#include <stdlib.h> + +extern int yylex(); +extern int yyparse(); +extern FILE* yyin; + +void yyerror(const char* s); +%} + +%union { + int ival; + float fval; +} + +%token<ival> T_INT +%token<fval> T_FLOAT +%token T_PLUS T_MINUS T_MULTIPLY T_DIVIDE T_LEFT T_RIGHT +%token T_NEWLINE T_QUIT +%left T_PLUS T_MINUS +%left T_MULTIPLY T_DIVIDE + +%type<ival> expression +%type<fval> mixed_expression + +%start calculation + +%% + +calculation: + | calculation line +; + +line: T_NEWLINE + | mixed_expression T_NEWLINE { printf("\tResult: %f\n", $1);} + | expression T_NEWLINE { printf("\tResult: %i\n", $1); } + | T_QUIT T_NEWLINE { printf("bye!\n"); exit(0); } +; + +mixed_expression: T_FLOAT { $$ = $1; } + | mixed_expression T_PLUS mixed_expression { $$ = $1 + $3; } + | mixed_expression T_MINUS mixed_expression { $$ = $1 - $3; } + | mixed_expression T_MULTIPLY mixed_expression { $$ = $1 * $3; } + | mixed_expression T_DIVIDE mixed_expression { $$ = $1 / $3; } + | T_LEFT mixed_expression T_RIGHT { $$ = $2; } + | expression T_PLUS mixed_expression { $$ = $1 + $3; } + | expression T_MINUS mixed_expression { $$ = $1 - $3; } + | expression T_MULTIPLY mixed_expression { $$ = $1 * $3; } + | expression T_DIVIDE mixed_expression { $$ = $1 / $3; } + | mixed_expression T_PLUS expression { $$ = $1 + $3; } + | mixed_expression T_MINUS expression { $$ = $1 - $3; } + | mixed_expression T_MULTIPLY expression { $$ = $1 * $3; } + | mixed_expression T_DIVIDE expression { $$ = $1 / $3; } + | expression T_DIVIDE expression { $$ = $1 / (float)$3; } +; + +expression: T_INT { $$ = $1; } + | expression T_PLUS expression { $$ = $1 + $3; } + | expression T_MINUS expression { $$ = $1 - $3; } + | expression T_MULTIPLY expression { $$ = $1 * $3; } + | T_LEFT expression T_RIGHT { $$ = $2; } +; + +%% + +int main() { + yyin = stdin; + + do { + yyparse(); + } while(!feof(yyin)); + + return 0; +} + +void yyerror(const char* s) { + fprintf(stderr, "Parse error: %s\n", s); + exit(1); +} diff --git a/tests/projects/lex_yacc/xmake.lua b/tests/projects/lex_yacc/xmake.lua new file mode 100644 index 000000000..21e1fa611 --- /dev/null +++ b/tests/projects/lex_yacc/xmake.lua @@ -0,0 +1,7 @@ + +add_rules("mode.debug", "mode.release") + +target("calc") + set_kind("binary") + add_rules("lex", "yacc") + add_files("src/*.l", "src/*.y") |
