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 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193
|
/* parser for CPC++ */
%{
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include "functions.h"
char st[1024];
int yylex(void);
int yyerror(const char* s);
extern int yylineno;
void set_input_string(const char* s);
void end_lexical_scan(void);
%}
%union {
int ival;
double dval;
char *sval;
}
// function tokens
%token FN_ABS
%token FN_INT
%token FN_SGN
// keywords tokens
%token KW_CLG
%token KW_CLS
%token KW_DRAWR
%token KW_DRAW
%token KW_FILL
%token KW_GPAPER // also used as function
%token KW_GPEN // also used as function
%token KW_INK
%token KW_LOCATE
%token KW_MODE // also used as function
%token KW_MOVER
%token KW_MOVE
%token KW_ORIGIN
%token KW_PAPER // also used as function
%token KW_PEN // also used as function
%token KW_PLOTR
%token KW_PLOT
%token KW_PRINT
// additionnals tokens
%token OP
%token CP
%token COMMA
%token COLON
%token SEMICOLON
%token <dval> NUMFLOAT
%token <ival> NUMINT
%token <sval> ALPHANUM
%token PLUS
%token MINUS
%token MUL
%token DIV
%token EDIV
%token MOD
%token EOL
%token GARBAGE
%type <dval> func param exp factor term
%type <ival> iparam
%type <sval> sparamlist sparam numstringparam strings2 strings1 string
%%
execute: /* nothing here */
| execute line EOL
| execute EOL
;
line: colons
| command
| command colons
| line command
| line command colons
;
colons: COLON
| colons COLON
;
command: KW_CLG { CPC_CLG(); }
| KW_CLS { CPC_CLS(); }
| KW_DRAWR iparam COMMA iparam COMMA iparam { CPC_DRAWR3($2, $4, $6); }
| KW_DRAWR iparam COMMA iparam { CPC_DRAWR2($2, $4); }
| KW_DRAW iparam COMMA iparam COMMA iparam { CPC_DRAW3($2, $4, $6); }
| KW_DRAW iparam COMMA iparam { CPC_DRAW2($2, $4); }
| KW_FILL iparam COMMA iparam COMMA iparam { CPC_FILL3($2, $4, $6); }
| KW_FILL iparam COMMA iparam { CPC_FILL2($2, $4); }
| KW_GPAPER iparam { CPC_GRAPHIC_PAPER($2); }
| KW_GPEN iparam { CPC_GRAPHIC_PEN($2); }
| KW_MOVER iparam COMMA iparam { CPC_MOVER($2, $4); }
| KW_MOVE iparam COMMA iparam { CPC_MOVE($2, $4); }
| KW_ORIGIN iparam COMMA iparam { CPC_ORIGIN($2, $4); }
| KW_INK iparam COMMA iparam { CPC_INK($2, $4); }
| KW_LOCATE iparam COMMA iparam { CPC_LOCATE($2, $4); }
| KW_MODE iparam { CPC_MODE($2); }
| KW_PAPER iparam { CPC_PAPER($2); }
| KW_PEN iparam { CPC_PEN($2); }
| KW_PLOTR iparam COMMA iparam COMMA iparam { CPC_PLOTR3($2, $4, $6); }
| KW_PLOTR iparam COMMA iparam { CPC_PLOTR2($2, $4); }
| KW_PLOT iparam COMMA iparam COMMA iparam { CPC_PLOT3($2, $4, $6); }
| KW_PLOT iparam COMMA iparam { CPC_PLOT2($2, $4); }
| KW_PRINT sparamlist { CPC_PRINT((char*)$2); }
;
sparamlist: sparam { $$ = $1; }
| sparamlist COMMA sparam { $$ = strcat($1, $3); }
;
sparam: strings1
| strings2
| numstringparam
;
numstringparam: param { if(round($1) != $1) { sprintf(st, "%f", $1); } else { sprintf(st, "%d", (int)$1); } $$ = (char*)st; }
;
func: FN_ABS OP param CP { $$ = fabs($3); }
| KW_MODE OP CP { $$ = (double)CPC_GET_MODE(); }
| KW_GPAPER OP CP { $$ = (double)CPC_GET_GRAPHIC_PAPER(); }
| KW_GPEN OP CP { $$ = (double)CPC_GET_GRAPHIC_PEN(); }
| FN_INT OP param CP { $$ = (double)CPC_INT($3); }
| KW_PAPER OP CP { $$ = (double)CPC_GET_PAPER(); }
| KW_PEN OP CP { $$ = (double)CPC_GET_PEN(); }
| FN_SGN OP param CP { $$ = (double)CPC_SGN($3); }
;
iparam: param { $$ = (int)round($1); }
;
param: exp
| PLUS exp { $$ = $2; }
| MINUS exp { $$ = -$2; }
;
exp: factor
| exp PLUS factor { $$ = $1 + $3; }
| exp MINUS factor { $$ = $1 - $3; }
;
factor: term
| factor MUL term { $$ = $1 * $3; }
| factor DIV term { $$ = $1 / $3; }
| factor EDIV term { $$ = (double)((int)((int)$1 / (int)$3)); }
| factor MOD term { $$ = (double)(((int)$1) % ((int)$3)); }
;
term: NUMINT { $$ = (double)$1; }
| NUMFLOAT
| func;
;
strings2: string SEMICOLON { $$ = $1;}
| strings2 string { $$ = strcat($1, $2);}
| strings2 string SEMICOLON { $$ = strcat($1, $2);}
;
strings1: string { $$ = $1;}
| strings1 PLUS string { $$ = strcat($1, $3);}
;
string: ALPHANUM { char* p = $$; p++; p[strlen(p) - 1] = 0; $$ = p; }
;
%%
int yyerror(const char *s) {
// show syntax error at line
//ed->SetError(ERR_SYNTAX_ERROR, "Syntax error", yylineno);
return 1;
}
// parses a string
int parse_string(const char* s) {
set_input_string(s);
int ret = yyparse();
end_lexical_scan();
return ret;
} |
Partager