OpenCores
URL https://opencores.org/ocsvn/zipcpu/zipcpu/trunk

Subversion Repositories zipcpu

[/] [zipcpu/] [trunk/] [sw/] [zasm/] [zpp.l] - Blame information for rev 13

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 13 dgisselq
/*******************************************************************************
2
**
3
** Filename:    zpp.l
4
**
5
** Project:     Zip CPU -- a small, lightweight, RISC CPU core
6
**
7
** Purpose:     The preprocessor for the Zip Assembler.
8
**
9
**      This routine strips comments, handles #define's, #ifdef's, and
10
**      #include statements in a C fashion.
11
**
12
**      #define macro's are also defined in the language and therefore
13
**      supposed to be supported, but the support isn't there yet.
14
**
15
** Creator:     Dan Gisselquist, Ph.D.
16
**              Gisselquist Tecnology, LLC
17
**
18
********************************************************************************
19
**
20
** Copyright (C) 2015, Gisselquist Technology, LLC
21
**
22
** This program is free software (firmware): you can redistribute it and/or
23
** modify it under the terms of  the GNU General Public License as published
24
** by the Free Software Foundation, either version 3 of the License, or (at
25
** your option) any later version.
26
**
27
** This program is distributed in the hope that it will be useful, but WITHOUT
28
** ANY WARRANTY; without even the implied warranty of MERCHANTIBILITY or
29
** FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
30
** for more details.
31
**
32
** You should have received a copy of the GNU General Public License along
33
** with this program.  (It's in the $(ROOT)/doc directory, run make with no
34
** target there if the PDF file isn't present.)  If not, see
35
**  for a copy.
36
**
37
** License:     GPL, v3, as defined and found on www.gnu.org,
38
**              http://www.gnu.org/licenses/gpl.html
39
**
40
**
41
*******************************************************************************/
42
 
43
%{
44
// #include 
45
#include 
46
#include 
47
#include 
48
#include 
49
 
50
using namespace std;
51
 
52
extern "C" int yylex();
53
// #include "zprepr.tab.h"
54
int     ndef = 0;
55
void    stb_define(const char *str);
56
void    stb_args(const char *str);
57
void    stb_macro(const char *value);
58
void    stb_addmacro(const char *value);
59
bool    stb_isdefined(const char *str);
60
const char      *stb_getdefn(const char *str);
61
%}
62
%x DEF DFA DFV INDEF IFDEFV INNOTDEF NODEF NVRDEF COMMENT
63
%x INDEF_EOL INNOTDEF_EOL
64
%option noyywrap
65
%option stack
66
ID [_:A-Za-z][_:A-Za-z0-9]*
67
 
68
%%
69
"*/"            { yy_pop_state(); }
70
[^*]+           { /* Ignore comments */ }
71
"*"+[^/]        { /* Ignore comments */ }
72
^"#include"[ \t]+\"[^\"]+\"     {
73
                char *ptr = &yytext[9], *start, *end, *str;
74
                while(isspace(*ptr))
75
                        ptr++;
76
                start = ptr;
77
                ptr++;
78
                while((*ptr)&&(*ptr != '\"'))
79
                        ptr++;
80
                *ptr = '\0';
81
                yypush_buffer_state(yy_create_buffer(
82
                                        fopen(start, "r"),
83
                                        YY_BUF_SIZE));
84
                // push_file_state(yylineno); // and filename ...
85
                fprintf(yyout, "#line 0 \"%s\"\n", start);
86
        }
87
^"#define"[ \t]+        { yy_push_state(DEF); }
88
 /* <*>^"#line"[ \t]+(0-9)+[ \t]+["][^"]*["][ \t]*\n       { } */
89
[_A-Za-z][_:A-Za-z0-9]*/[^(]    {
90
                stb_define(yytext);
91
                BEGIN DFV;
92
        }
93
{ID}/[(]        { fprintf(stderr, "DEF::Found MACRO\n");
94
                stb_define(yytext);
95
                BEGIN DFA; }
96
([^)]+)                         {
97
                /* Process arguments */
98
                stb_args(yytext);
99
                BEGIN DFV;
100
        }
101
[ \t]+  { /* Ignore initial spaces */ }
102
[.]*$   {/* Parse to end of line, get value for our define */
103
                // printf("End of define, value = \'%s\'\n", yytext);
104
                stb_macro(yytext);
105
                yy_pop_state();
106
        }
107
^[ \t]+.[dD][aA][tT][aA]?       { fprintf(yyout, "\tWORD"); }
108
^"#defcont"[ \t]+       { yy_push_state(DFV); }
109
^"#ifdef"[ \t]* { ndef = 0; yy_push_state(IFDEFV); }
110
^"#ifndef"[ \t]*        { ndef = 1; yy_push_state(IFDEFV); }
111
{ID}    {
112
                bool    known = stb_isdefined(yytext);
113
                if ( ((known)&&(ndef==0)) || ((!known)&&(ndef!=0)) ) {
114
                        BEGIN INDEF_EOL;
115
                } else {
116
                        BEGIN INNOTDEF_EOL;
117
                }
118
        }
119
        /* Not yet: ^"#if"[ \t]*                { yy_push_state(IFDEFE); }
120
        /* Not yet: ^"#if"[ \t]*                { yy_push_state(IFDEFE); }
121
        /* Not yet:  { yy_push_state(IFDEFE); } */
122
        /* ^"#elsif"[ \t]*      { yy_pop_state(); yy_push_state(IFDEFE); } */
123
[ \t]*$         { BEGIN INDEF; }
124
(;|"//").*$             { BEGIN INDEF; }
125
[ \t]*$         { BEGIN INNOTDEF; }
126
(;|"//").*$     { BEGIN INNOTDEF; }
127
[^ \t\n].*$             { BEGIN INDEF; fprintf(stderr, "WARNING! Unexpected characters on IFDEF line, \'%s\'\n", yytext); }
128
[^ \t\n].*$     { BEGIN INNOTDEF; fprintf(stderr, "WARNING! Unexpected characters on IFNDEF line, %s\n", yytext); }
129
^"#else"[ \t]*((;|"//").*)?$    { BEGIN NODEF; }
130
^"#else"[ \t]*((;|"//").*)?$            { BEGIN INDEF; }
131
(.*)                    { }
132
^"#elsif"[ \t]*         { BEGIN NVRDEF; }
133
^"#endif"[ \t]*((;|"//").*)?$   { yy_pop_state(); }
134
^"#endif"[ \t]*"/*"     { BEGIN COMMENT; }
135
<*>^"#endif"[ \t]*         { fprintf(stderr, "ERR: Unknown endif!!\n");}
136
        /* Not yet: ^"#struct"[ \t]*    {}      */
137
        /* Not yet: ^"#endstruct"[ \t]* {}      */
138
        /* Not yet: ^"#seg"[ \t]*       {}      */
139
.*              { /* Ignore everything in these states*/ }
140
{ID}/[^(]       {
141
                if (stb_isdefined(yytext))
142
                        fprintf(yyout, "%s", stb_getdefn(yytext));
143
                else
144
                        fprintf(yyout, "%s", yytext);
145
        }
146
<*>^[ \t]*"//".*$  { /* Ignore comment only lines */ }
147
<*>^[ \t]*";".*$   { /* Ignore comment only lines */ }
148
<*>"//".*          { /* Ignore trailing comments */ }
149
<*>";".*           { /* Ignore trailing comments */ }
150
<*>"/*"                    { yy_push_state(COMMENT); }
151
<*>[ \t]+          { ECHO; }
152
[.]*    { ECHO; }
153
<*>\n                      { ECHO; }
154
        /* <*>.                    { printf("Unmatched \'%c\'\n", yytext[0]); } */
155
        /* <>                    { printf("EOF!\n"); } */
156
 
157
%%
158
 
159
class   SYMTABLE_ENTRY {
160
private:
161
        std::string     &trim(std::string &s) {
162
                std::string::iterator   ptr = s.end();
163
 
164
                while((ptr >= s.begin())&&(isspace(*ptr)))
165
                        *ptr-- = '\0';
166
 
167
                return s;
168
        }
169
 
170
public:
171
        std::string     m_name, m_value, m_args;
172
        SYMTABLE_ENTRY(const char *str) : m_name(str) {
173
                trim(m_name);
174
        }
175
        SYMTABLE_ENTRY &operator+=(const char *str) {
176
                const char      *start = str;
177
 
178
                while(isspace(*start))
179
                        start++;
180
                if (m_value.length()!=0)
181
                        m_value += " ";
182
 
183
                std::string     trimd(start);
184
                trim(trimd);
185
                m_value += trimd;
186
 
187
                /*
188
                printf("ENTRY::SYMBOL \'%s\' NOW = \'%s\'\n",
189
                        m_name.c_str(), m_value.c_str());
190
                */
191
                return *this;
192
        }
193
        SYMTABLE_ENTRY &setargs(const char *str) {
194
                m_args += str;
195
                return *this;
196
        }
197
 
198
        std::string     getdefn(void) {
199
                return m_value;
200
        }
201
};
202
 
203
class   SYMBOL_TABLE {
204
private:
205
        typedef SYMTABLE_ENTRY  *TBLV;
206
        typedef std::list       TBLT;
207
 
208
        TBLT    m_tbl;
209
        TBLT::iterator  lookup(const char *str) {
210
                TBLT::iterator  i = m_tbl.begin();
211
                for(; (i!= m_tbl.end())&&(strcmp(str, (*i)->m_name.c_str())>0); i++)
212
                        ;
213
                if ((i != m_tbl.end())&&(strcmp(str, (*i)->m_name.c_str())==0))
214
                        return i;
215
                return m_tbl.end();
216
        }
217
 
218
public:
219
        SYMBOL_TABLE(void) {}
220
 
221
        void define(const char *str) {
222
                SYMTABLE_ENTRY  *v = new SYMTABLE_ENTRY(str);
223
                TBLT::iterator  i = m_tbl.begin();
224
                for(; (i!= m_tbl.end())&&(strcmp(str, (*i)->m_name.c_str())>0); i++)
225
                        ;
226
                m_tbl.insert(i, v);
227
 
228
                // printf("SYMS::Defining SYMBOL: \'%s\'\n", str);
229
        }
230
 
231
        bool defined(const char *str) {
232
                TBLT::iterator  i = lookup(str);
233
                if (i==m_tbl.end())
234
                        return false;
235
                else
236
                        return true;
237
        }
238
 
239
 
240
        void    undefine(const char *str) {
241
                TBLT::iterator  i = lookup(str);
242
                if (i == m_tbl.end())
243
                        return;
244
                TBLV    v = (*i);
245
                m_tbl.erase(i);
246
                delete  v;
247
        }
248
 
249
        void    addmacro(const char *name, const char *str) {
250
                TBLT::iterator i = lookup(name);
251
                if (i == m_tbl.end()) {
252
                        fprintf(stderr, "INTERNAL ERR, %s NOT DEFINED!\n", name);
253
                } *(*i) += str;
254
        }
255
 
256
        void    addargs(const char *name, const char *str) {
257
                TBLT::iterator i = lookup(name);
258
                if (i == m_tbl.end()) {
259
                        fprintf(stderr, "INTERNAL ERR, %s NOT DEFINED!\n", name);
260
                } (*i)->setargs(str);
261
        }
262
        const   char *getdefn(const char *name) {
263
                TBLT::iterator i = lookup(name);
264
                if (i == m_tbl.end()) {
265
                        fprintf(stderr, "INTERNAL ERR, %s NOT DEFINED!\n", name);
266
                        return NULL;
267
                } (*i)->getdefn().c_str();
268
        }
269
 
270
};
271
 
272
SYMTABLE_ENTRY  *last = NULL;
273
SYMBOL_TABLE    syms;
274
std::string     last_define;
275
 
276
void    stb_define(const char *str) {
277
        if (syms.defined(str)) {
278
                fprintf(stderr, "WARNING!  Symbol \'%s\' is already defined!\n", str);
279
                syms.undefine(str);
280
        }
281
 
282
        syms.define(str);
283
        last_define = str;
284
}
285
 
286
void    stb_args(const char *args) {
287
        syms.addargs(last_define.c_str(), args);
288
}
289
 
290
void    stb_macro(const char *value) {
291
        syms.addmacro(last_define.c_str(), value);
292
}
293
 
294
void    stb_addmacro(const char *value) {
295
        syms.addmacro(last_define.c_str(),value);
296
}
297
 
298
bool    stb_isdefined(const char *str) {
299
        return syms.defined(str);
300
}
301
 
302
const char *stb_getdefn(const char *str) {
303
        return syms.getdefn(str);
304
}
305
 
306
int main(int argc, char **argv) {
307
        yylex();
308
}
309
 

powered by: WebSVN 2.1.0

© copyright 1999-2022 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.