ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/group/trunk/OOPSE-1.0/libBASS/BASSlex.l
Revision: 1334
Committed: Fri Jul 16 18:58:03 2004 UTC (19 years, 11 months ago) by gezelter
File size: 9576 byte(s)
Log Message:
Initial import of OOPSE-1.0 source tree

File Contents

# User Rev Content
1 gezelter 1334
2     /* define some search patterns */
3    
4     digit [0-9]
5     letter [A-Za-z]
6     natural {digit}+
7     signedNat ("+"|"-")?{natural}
8     number {signedNat}("."{natural})?([Ee]{signedNat})?
9     identifier ("_"|{letter})({letter}|{digit}|"-"|"_")*
10    
11     /* define start states */
12    
13     %x PRE_P
14     %x INCL
15     %x DEF
16     %x IFDEF
17     %x IFNDEF
18     %x ESCAPE
19     %x CHECK_ESCAPE
20    
21     /* what to put at the top of the lex code */
22    
23     %{
24     #include <stdlib.h>
25     #include <stdio.h>
26     #include <string.h>
27    
28     #include "BASSyacc.h"
29     #include "BASS_parse.h"
30     #include "simError.h"
31     #ifdef IS_MPI
32     #define __is_lex__
33     #include "mpiBASS.h"
34     #endif
35    
36     typedef unsigned short int r_short;
37     typedef unsigned short my_short;
38    
39     extern void change_in_file( FILE* in_file );
40    
41     // the following is used by the include start state
42    
43     #define MAX_BUFFER_DEPTH 10
44     YY_BUFFER_STATE buffer_stack[MAX_BUFFER_DEPTH]; // a stack of the include buffers
45     int buffer_stack_ptr = 0;
46     struct filename_list{
47     char my_name[300];
48     struct filename_list* next;
49     };
50     struct filename_list* yyfile_name;
51     struct filename_list* temp_yyfile_name;
52     int yylineno_stack[MAX_BUFFER_DEPTH];
53    
54    
55     // the following is a check against the define buffer length
56    
57     void check_def_buff( char* defined, int index );
58    
59     //these are used by the ifdef and ifndef statements
60    
61     int escape_stack_ptr = 0; //keeps track of the escape stack
62    
63    
64     %}
65    
66     %option yylineno
67    
68     %%
69    
70     {signedNat} {
71     yylval.i_val = atoi( yytext );
72     return INTEGER;
73     }
74    
75     {number} {
76     yylval.d_val = atof( yytext );
77     return DOUBLE;
78     }
79    
80     {identifier} {
81     int token;
82     token = res_word( yytext );
83    
84     if( token == DEFINED ){
85    
86     if( buffer_stack_ptr >= MAX_BUFFER_DEPTH ){
87     fprintf( stderr,
88     "Maximum buffer depth exceeded for %s.\n",
89     yytext );
90     exit(1);
91     }
92    
93     buffer_stack[buffer_stack_ptr] = YY_CURRENT_BUFFER;
94     buffer_stack_ptr++;
95    
96     yy_scan_string( get_definition( yytext ) );
97     }
98     else if( token ){
99     return token;
100     }
101     else{
102     yylval.s_ptr = strdup( yytext );
103     return IDENTIFIER;
104     }
105     }
106    
107     \".*\" {
108     /* little routine to strip off the quotes */
109    
110     my_short i;
111     i = 0; // index
112     while( yytext[i+1] != '\"' ){
113    
114     yytext[i] = yytext[i+1];
115     i++;
116     }
117     yytext[i] = '\0';
118     yylval.s_ptr = strdup( yytext );
119     return QUOTED_STRING;
120     }
121    
122     \(.*\) {
123     /* little routine to pass a list string */
124    
125     my_short i;
126     i = 0; // index
127     while( yytext[i+1] != ')' ){
128    
129     yytext[i] = yytext[i+1];
130     i++;
131     }
132     yytext[i] = '\0';
133     yylval.s_ptr = strdup( yytext );
134     return LIST_STRING;
135     }
136    
137     \[{natural}\] {
138     int index;
139     sscanf(yytext, "[%d]", &index);
140     yylval.i_val = index;
141     return ARRAY_INDEX;
142     }
143    
144     [ \t\n]+ /* ignore whitespace */;
145    
146     "/*" {
147     /* ignore comments */
148     my_short done;
149     char c;
150    
151     done = 0;
152     while( !done ){
153    
154     c = input();
155     while( c != '*' ){
156    
157     c = input();
158     }
159     while( c == '*' ){
160    
161     c = input();
162     }
163     if( c == '/' ) done = 1;
164     }
165     }
166    
167     "//".*\n /* ignore comments */;
168    
169     "#" BEGIN(PRE_P);
170    
171     . {
172     // pass everything else to yacc
173     return yytext[0];
174     }
175    
176     <PRE_P>"include" BEGIN(INCL);
177     <PRE_P>"define" BEGIN(DEF);
178     <PRE_P>"ifdef" BEGIN(IFDEF);
179     <PRE_P>"ifndef" BEGIN(IFNDEF);
180     <PRE_P>"endif" /* do nothing */;
181     <PRE_P>\n BEGIN(INITIAL);
182    
183     <INCL>[ \t]* /* eat white space */
184     <INCL>\".*\" {
185     char foo_name[300];
186    
187     // little routine to strip off the quotes
188    
189     my_short i;
190     i = 0; // index
191     while( yytext[i+1] != '\"' ){
192    
193     yytext[i] = yytext[i+1];
194     i++;
195     }
196    
197     yytext[i] = '\0';
198     strcpy( foo_name, yytext );
199    
200     // now we have the include file name
201    
202     if( buffer_stack_ptr >= MAX_BUFFER_DEPTH ){
203    
204     fprintf( stderr, "Includes nested too deeply\n" );
205     exit(1);
206     }
207    
208     buffer_stack[buffer_stack_ptr] = YY_CURRENT_BUFFER;
209     yylineno_stack[buffer_stack_ptr] = yylineno;
210     buffer_stack_ptr++;
211    
212     yyin = fopen( yytext, "r" );
213     if( yyin == NULL ){
214     fprintf( stderr, "Unable to include file %s\n", yytext );
215     exit(1);
216     }
217    
218     yy_switch_to_buffer( yy_create_buffer( yyin, YY_BUF_SIZE ) );
219     yylineno = 0;
220    
221     temp_yyfile_name = (struct filename_list* )malloc( sizeof( struct filename_list ) );
222     temp_yyfile_name->next = yyfile_name;
223     yyfile_name = temp_yyfile_name;
224     strcpy( yyfile_name->my_name, foo_name );
225    
226    
227     BEGIN(INITIAL);
228     }
229     <INCL>\n BEGIN(INITIAL);
230     <INCL>. /* ignore everything else */
231    
232     <DEF>[ \t]* /* eat white space */;
233     <DEF>{identifier} {
234     char c;
235     char definition[ DEFINED_BUFFER_SIZE ];
236     short int done;
237     short int c_done; // a done marker for the comments
238     int def_ptr;
239    
240     // initialize the definition buffer
241    
242     for( def_ptr = 0; def_ptr < DEFINED_BUFFER_SIZE; def_ptr++ ){
243     definition[def_ptr] = '\0';
244     }
245    
246     def_ptr =0;
247     done = 0;
248     c_done = 0;
249    
250     while( !done ){
251    
252     c = input();
253     if( c == '\"' ){
254    
255     // shove the whole quoted string into the macro
256    
257     definition[def_ptr] = c;
258     //fprintf( stderr, "%c", c );
259     def_ptr++;
260     check_def_buff( yytext, def_ptr );
261    
262     c = input();
263     while( c != '\"' ){
264    
265     definition[def_ptr] = c;
266     //fprintf( stderr, "%c", c );
267     def_ptr++;
268     check_def_buff( yytext, def_ptr );
269    
270     c = input();
271     }
272     definition[def_ptr] = c;
273     //fprintf( stderr, "%c", c );
274     def_ptr++;
275     check_def_buff( yytext, def_ptr );
276     c = input();
277     }
278    
279     // handle comments
280    
281     if( c == '/' ){
282     c = input();
283     switch( c ){
284    
285     case '/':
286     while( c != '\n' && c != '\\' ){
287     c = input();
288     }
289     break;
290    
291     case '*':
292     c_done = 0;
293     while( !c_done ){
294     c = input();
295     while( c != '*' ){
296     c = input();
297     }
298     while( c == '*' ){
299     c = input();
300     }
301     if( c == '/' ) c_done = 1;
302     }
303     c = input();
304     break;
305    
306     default:
307     // the '/' char was a normal symbol
308     definition[def_ptr] = '/';
309     //fprintf( stderr, "%c", c );
310     def_ptr++;
311     check_def_buff( yytext, def_ptr );
312     break;
313     }
314     }
315    
316    
317     if( c == '\n' ){
318     done = 1;
319     }
320    
321     else{
322    
323     // check for the line wrap character '\'
324    
325     if( c == '\\' ){
326    
327     // skip the rest of the line until the line return
328    
329     c = input();
330     while( c != '\n' ){
331     c = input();
332     }
333     }
334    
335     else{
336    
337     // we now know the character is a good one
338    
339     definition[def_ptr] = c;
340     //fprintf( stderr, "%c", c );
341     def_ptr++;
342     check_def_buff( yytext, def_ptr );
343     }
344     }
345     }
346    
347     insert_define( yytext, definition );
348     BEGIN(INITIAL);
349     }
350     <DEF>\n BEGIN(INITIAL);
351     <DEF>. /* ignore everything else */;
352    
353     <IFDEF>[ \t]* /* eat white space */;
354     <IFDEF>{identifier} {
355     if( !is_defined( yytext ) ){
356     escape_stack_ptr++;
357     BEGIN(ESCAPE);
358     }
359     }
360     <IFDEF>\n BEGIN(INITIAL);
361     <IFDEF>. /* ignore everything else */;
362    
363     <IFNDEF>[ \t]* /* eat the white space */;
364     <IFNDEF>{identifier} {
365     if( is_defined( yytext ) ){
366     escape_stack_ptr++;
367     BEGIN(ESCAPE);
368     }
369     }
370     <IFNDEF>\n BEGIN(INITIAL);
371     <IFNDEF>. /* ignore everything else */;
372    
373     <ESCAPE>\".*\" /* do nothing */;
374     <ESCAPE>"//".*\n /* ignore comments */;
375     <ESCAPE>"/*" {
376     /* ignore comments */
377     my_short done;
378     char c;
379    
380     done = 0;
381     while( !done ){
382    
383     c = input();
384     while( c != '*' ){
385    
386     c = input();
387     }
388    
389     while( c == '*' ){
390    
391     c = input();
392     }
393    
394     if( c == '/' ) done = 1;
395     }
396     }
397     <ESCAPE>"#" BEGIN(CHECK_ESCAPE);
398     <ESCAPE>. /* ignore everything else */;
399    
400     <CHECK_ESCAPE>[ \t] /* ignore whitespace */;
401     <CHECK_ESCAPE>"ifdef" { escape_stack_ptr++; BEGIN(ESCAPE); }
402     <CHECK_ESCAPE>"ifndef" { escape_stack_ptr++; BEGIN(ESCAPE); }
403     <CHECK_ESCAPE>"endif" {
404     escape_stack_ptr--;
405     if( escape_stack_ptr <= 0){
406     escape_stack_ptr = 0; // just in case something flubbed
407     BEGIN(INITIAL);
408     }
409     }
410     <CHECK_ESCAPE>\n BEGIN(ESCAPE);
411     <CHECK_ESCAPE>. /* ignore everything else */;
412    
413     <<EOF>> {
414     buffer_stack_ptr--;
415     if( buffer_stack_ptr < 0 ){
416    
417     yyterminate();
418     }
419    
420     else{
421    
422     yy_delete_buffer( YY_CURRENT_BUFFER );
423     yy_switch_to_buffer( buffer_stack[buffer_stack_ptr] );
424     yylineno = yylineno_stack[buffer_stack_ptr];
425    
426     temp_yyfile_name = yyfile_name;
427     yyfile_name = temp_yyfile_name->next;
428     free( temp_yyfile_name );
429     }
430     }
431    
432     %%
433    
434     void check_def_buff( char* defined, int index ){
435    
436     if( index >= DEFINED_BUFFER_SIZE ){
437    
438     sprintf( painCave.errMsg, "Define buffer size exceeded for %s\n", defined );
439     painCave.isFatal = 1;
440     simError();
441     }
442     }
443    
444     int yywrap(void){
445     return 1;
446     }
447    
448     void change_in_file( FILE* in_file ){
449    
450     yyin = in_file;
451     }