-
Notifications
You must be signed in to change notification settings - Fork 0
/
pancake.l
127 lines (114 loc) · 3.61 KB
/
pancake.l
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
%{
/* Pancake - C implementation of the Pancake programming language.
Copyright (C) 2013 Uiri Noyb
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
#include <ctype.h>
#include "mylist.h"
#include "pancake.y.h"
#undef YY_BUF_SIZE
#define YY_BUF_SIZE 128
int lineno = 1;
extern YYSTYPE yylval;
int yyleng;
int fdef = 0;
extern List* buffernames;
extern int yywrap(void) { return 1;}
extern void yyerror(const char* msg);
%}
%option noinput
%option nounput
%%
\"[^\"]*\" { int i;yylval.symbol = malloc(yyleng+1);
for(i=0;i<yyleng;i++) yylval.symbol[i] = yytext[i];
yylval.symbol[yyleng] = '\0';
return STR; }
'[^']*'' { int i;yylval.symbol = malloc(yyleng+1);
for(i=0;i<yyleng;i++) yylval.symbol[i] = yytext[i];
yylval.symbol[yyleng] = '\0';
return STR; }
@[-A-Za-z0-9]+ { int i;char* filename; yyleng--;
filename = malloc(yyleng+4);
for (i=0;i<yyleng;i++)
filename[i] = yytext[i+1];
filename[i] = '.'; i++;
filename[i] = 'p'; i++;
filename[i] = 'c'; i++;
filename[i] = '\0';
yyin = fopen(filename, "r");
if (!yyin) yyerror(filename);
for (i=0;i<yyleng;i++)
filename[i] = toupper(yytext[i+1]);
filename[yyleng+1] = '\0';
addToListEnd(buffernames, filename);
yylval.symbol = filename;
yypush_buffer_state(yy_create_buffer( yyin, YY_BUF_SIZE));
}
[\.,()[\]:<>=&|!] { return yytext[0]; }
_ { fdef = 1; return yytext[0]; }
; {
free(dataInListEnd(buffernames));
deleteFromListEnd(buffernames);
return yytext[0];
}
\* { fdef = 0; return yytext[0]; }
-?[0-9]+ { yylval.integer = atoi((char *)yytext);
return INT;
}
[A-Z][A-Za-z0-9]* { int i, l; char* namespace = NULL;
if (fdef)
namespace = dataInListEnd(buffernames);
if (namespace != NULL) {
l = strlen(namespace); l++;
} else
l = 0;
yylval.symbol = malloc(yyleng+l+1);
if (namespace != NULL) {
l--;
for (i=0;i<l;i++)
yylval.symbol[i] = namespace[i];
}
for (i=0;i<yyleng;i++)
yylval.symbol[l+i] = toupper(yytext[i]);
yylval.symbol[yyleng+l] = '\0';
if (fdef) {
fdef = 0;
namespace = malloc(yyleng+l+2);
namespace[yyleng+l] = '.';
namespace[yyleng+l+1] = '\0';
for (i=0;i<yyleng+l;i++)
namespace[i] = yylval.symbol[i];
addToListEnd(buffernames, namespace);
}
fdef = 0;
return FUNC;
}
[a-z][A-Za-z0-9]* { int i;yylval.symbol = malloc(yyleng+1);
for (i=0;i<yyleng;i++)
yylval.symbol[i] = tolower(yytext[i]);
yylval.symbol[yyleng] = '\0';
return VAR;
}
\#\#([^\#]+\#?)+\#\# { int i; for(i=0;i<yyleng;i++) if (yytext[i] == 10) lineno++;}
\#.* ;
[ \t] ;
\n lineno++;
. { printf("Illegal character: %c", yytext[0]); yyerror(":("); }
<<EOF>> { fclose(yyin); yypop_buffer_state();
if (!YY_CURRENT_BUFFER) {
yyterminate();
} else if (buffernames->next != NULL) {
free(dataInListEnd(buffernames));
deleteFromListEnd(buffernames);
}
}
%%