source: trunk/third/flex/main.c @ 16044

Revision 16044, 28.1 KB checked in by ghudson, 24 years ago (diff)
This commit was generated by cvs2svn to compensate for changes in r16043, which included commits to RCS files with non-trunk default branches.
Line 
1/* flex - tool to generate fast lexical analyzers */
2
3/*-
4 * Copyright (c) 1990 The Regents of the University of California.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to Berkeley by
8 * Vern Paxson.
9 *
10 * The United States Government has rights in this work pursuant
11 * to contract no. DE-AC03-76SF00098 between the United States
12 * Department of Energy and the University of California.
13 *
14 * Redistribution and use in source and binary forms with or without
15 * modification are permitted provided that: (1) source distributions retain
16 * this entire copyright notice and comment, and (2) distributions including
17 * binaries display the following acknowledgement:  ``This product includes
18 * software developed by the University of California, Berkeley and its
19 * contributors'' in the documentation or other materials provided with the
20 * distribution and in all advertising materials mentioning features or use
21 * of this software.  Neither the name of the University nor the names of
22 * its contributors may be used to endorse or promote products derived from
23 * this software without specific prior written permission.
24 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
25 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
26 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
27 */
28
29#ifndef lint
30char copyright[] =
31"@(#) Copyright (c) 1990 The Regents of the University of California.\n\
32 All rights reserved.\n";
33#endif /* not lint */
34
35/* $Header: /afs/dev.mit.edu/source/repository/third/flex/main.c,v 1.1.1.1 2001-04-10 17:05:15 ghudson Exp $ */
36
37
38#include "flexdef.h"
39#include "version.h"
40
41static char flex_version[] = FLEX_VERSION;
42
43
44/* declare functions that have forward references */
45
46void flexinit PROTO((int, char**));
47void readin PROTO((void));
48void set_up_initial_allocations PROTO((void));
49
50#ifdef NEED_ARGV_FIXUP
51extern void argv_fixup PROTO((int *, char ***));
52#endif
53
54
55/* these globals are all defined and commented in flexdef.h */
56int printstats, syntaxerror, eofseen, ddebug, trace, nowarn, spprdflt;
57int interactive, caseins, lex_compat, do_yylineno, useecs, fulltbl, usemecs;
58int fullspd, gen_line_dirs, performance_report, backing_up_report;
59int C_plus_plus, long_align, use_read, yytext_is_array, do_yywrap, csize;
60int yymore_used, reject, real_reject, continued_action, in_rule;
61int yymore_really_used, reject_really_used;
62int datapos, dataline, linenum, out_linenum;
63FILE *skelfile = NULL;
64int skel_ind = 0;
65char *action_array;
66int action_size, defs1_offset, prolog_offset, action_offset, action_index;
67char *infilename = NULL, *outfilename = NULL;
68int did_outfilename;
69char *prefix, *yyclass;
70int do_stdinit, use_stdout;
71int onestate[ONE_STACK_SIZE], onesym[ONE_STACK_SIZE];
72int onenext[ONE_STACK_SIZE], onedef[ONE_STACK_SIZE], onesp;
73int current_mns, current_max_rules;
74int num_rules, num_eof_rules, default_rule, lastnfa;
75int *firstst, *lastst, *finalst, *transchar, *trans1, *trans2;
76int *accptnum, *assoc_rule, *state_type;
77int *rule_type, *rule_linenum, *rule_useful;
78int current_state_type;
79int variable_trailing_context_rules;
80int numtemps, numprots, protprev[MSP], protnext[MSP], prottbl[MSP];
81int protcomst[MSP], firstprot, lastprot, protsave[PROT_SAVE_SIZE];
82int numecs, nextecm[CSIZE + 1], ecgroup[CSIZE + 1], nummecs, tecfwd[CSIZE + 1];
83int tecbck[CSIZE + 1];
84int lastsc, *scset, *scbol, *scxclu, *sceof;
85int current_max_scs;
86char **scname;
87int current_max_dfa_size, current_max_xpairs;
88int current_max_template_xpairs, current_max_dfas;
89int lastdfa, *nxt, *chk, *tnxt;
90int *base, *def, *nultrans, NUL_ec, tblend, firstfree, **dss, *dfasiz;
91union dfaacc_union *dfaacc;
92int *accsiz, *dhash, numas;
93int numsnpairs, jambase, jamstate;
94int lastccl, *cclmap, *ccllen, *cclng, cclreuse;
95int current_maxccls, current_max_ccl_tbl_size;
96Char *ccltbl;
97char nmstr[MAXLINE];
98int sectnum, nummt, hshcol, dfaeql, numeps, eps2, num_reallocs;
99int tmpuses, totnst, peakpairs, numuniq, numdup, hshsave;
100int num_backing_up, bol_needed;
101FILE *backing_up_file;
102int end_of_buffer_state;
103char **input_files;
104int num_input_files;
105
106/* Make sure program_name is initialized so we don't crash if writing
107 * out an error message before getting the program name from argv[0].
108 */
109char *program_name = "flex";
110
111#ifndef SHORT_FILE_NAMES
112static char *outfile_template = "lex.%s.%s";
113static char *backing_name = "lex.backup";
114#else
115static char *outfile_template = "lex%s.%s";
116static char *backing_name = "lex.bck";
117#endif
118
119#ifdef THINK_C
120#include <console.h>
121#endif
122
123#ifdef MS_DOS
124extern unsigned _stklen = 16384;
125#endif
126
127static char outfile_path[MAXLINE];
128static int outfile_created = 0;
129static char *skelname = NULL;
130
131
132int main( argc, argv )
133int argc;
134char **argv;
135        {
136        int i;
137
138#ifdef THINK_C
139        argc = ccommand( &argv );
140#endif
141#ifdef NEED_ARGV_FIXUP
142        argv_fixup( &argc, &argv );
143#endif
144
145        flexinit( argc, argv );
146
147        readin();
148
149        ntod();
150
151        for ( i = 1; i <= num_rules; ++i )
152                if ( ! rule_useful[i] && i != default_rule )
153                        line_warning( _( "rule cannot be matched" ),
154                                        rule_linenum[i] );
155
156        if ( spprdflt && ! reject && rule_useful[default_rule] )
157                line_warning(
158                        _( "-s option given but default rule can be matched" ),
159                        rule_linenum[default_rule] );
160
161        /* Generate the C state transition tables from the DFA. */
162        make_tables();
163
164        /* Note, flexend does not return.  It exits with its argument
165         * as status.
166         */
167        flexend( 0 );
168
169        return 0;       /* keep compilers/lint happy */
170        }
171
172
173/* check_options - check user-specified options */
174
175void check_options()
176        {
177        int i;
178
179        if ( lex_compat )
180                {
181                if ( C_plus_plus )
182                        flexerror( _( "Can't use -+ with -l option" ) );
183
184                if ( fulltbl || fullspd )
185                        flexerror( _( "Can't use -f or -F with -l option" ) );
186
187                /* Don't rely on detecting use of yymore() and REJECT,
188                 * just assume they'll be used.
189                 */
190                yymore_really_used = reject_really_used = true;
191
192                yytext_is_array = true;
193                do_yylineno = true;
194                use_read = false;
195                }
196
197        if ( do_yylineno )
198                /* This should really be "maintain_backup_tables = true" */
199                reject_really_used = true;
200
201        if ( csize == unspecified )
202                {
203                if ( (fulltbl || fullspd) && ! useecs )
204                        csize = DEFAULT_CSIZE;
205                else
206                        csize = CSIZE;
207                }
208
209        if ( interactive == unspecified )
210                {
211                if ( fulltbl || fullspd )
212                        interactive = false;
213                else
214                        interactive = true;
215                }
216
217        if ( fulltbl || fullspd )
218                {
219                if ( usemecs )
220                        flexerror(
221                        _( "-Cf/-CF and -Cm don't make sense together" ) );
222
223                if ( interactive )
224                        flexerror( _( "-Cf/-CF and -I are incompatible" ) );
225
226                if ( lex_compat )
227                        flexerror(
228                _( "-Cf/-CF are incompatible with lex-compatibility mode" ) );
229
230                if ( do_yylineno )
231                        flexerror(
232                        _( "-Cf/-CF and %option yylineno are incompatible" ) );
233
234                if ( fulltbl && fullspd )
235                        flexerror( _( "-Cf and -CF are mutually exclusive" ) );
236                }
237
238        if ( C_plus_plus && fullspd )
239                flexerror( _( "Can't use -+ with -CF option" ) );
240
241        if ( C_plus_plus && yytext_is_array )
242                {
243                warn( _( "%array incompatible with -+ option" ) );
244                yytext_is_array = false;
245                }
246
247        if ( useecs )
248                { /* Set up doubly-linked equivalence classes. */
249
250                /* We loop all the way up to csize, since ecgroup[csize] is
251                 * the position used for NUL characters.
252                 */
253                ecgroup[1] = NIL;
254
255                for ( i = 2; i <= csize; ++i )
256                        {
257                        ecgroup[i] = i - 1;
258                        nextecm[i - 1] = i;
259                        }
260
261                nextecm[csize] = NIL;
262                }
263
264        else
265                {
266                /* Put everything in its own equivalence class. */
267                for ( i = 1; i <= csize; ++i )
268                        {
269                        ecgroup[i] = i;
270                        nextecm[i] = BAD_SUBSCRIPT;     /* to catch errors */
271                        }
272                }
273
274        if ( ! use_stdout )
275                {
276                FILE *prev_stdout;
277
278                if ( ! did_outfilename )
279                        {
280                        char *suffix;
281
282                        if ( C_plus_plus )
283                                suffix = "cc";
284                        else
285                                suffix = "c";
286
287                        sprintf( outfile_path, outfile_template,
288                                prefix, suffix );
289
290                        outfilename = outfile_path;
291                        }
292
293                prev_stdout = freopen( outfilename, "w", stdout );
294
295                if ( prev_stdout == NULL )
296                        lerrsf( _( "could not create %s" ), outfilename );
297
298                outfile_created = 1;
299                }
300
301        if ( skelname && (skelfile = fopen( skelname, "r" )) == NULL )
302                lerrsf( _( "can't open skeleton file %s" ), skelname );
303
304        if ( strcmp( prefix, "yy" ) )
305                {
306#define GEN_PREFIX(name) out_str3( "#define yy%s %s%s\n", name, prefix, name )
307                if ( C_plus_plus )
308                        GEN_PREFIX( "FlexLexer" );
309                else
310                        {
311                        GEN_PREFIX( "_create_buffer" );
312                        GEN_PREFIX( "_delete_buffer" );
313                        GEN_PREFIX( "_scan_buffer" );
314                        GEN_PREFIX( "_scan_string" );
315                        GEN_PREFIX( "_scan_bytes" );
316                        GEN_PREFIX( "_flex_debug" );
317                        GEN_PREFIX( "_init_buffer" );
318                        GEN_PREFIX( "_flush_buffer" );
319                        GEN_PREFIX( "_load_buffer_state" );
320                        GEN_PREFIX( "_switch_to_buffer" );
321                        GEN_PREFIX( "in" );
322                        GEN_PREFIX( "leng" );
323                        GEN_PREFIX( "lex" );
324                        GEN_PREFIX( "out" );
325                        GEN_PREFIX( "restart" );
326                        GEN_PREFIX( "text" );
327
328                        if ( do_yylineno )
329                                GEN_PREFIX( "lineno" );
330                        }
331
332                if ( do_yywrap )
333                        GEN_PREFIX( "wrap" );
334
335                outn( "" );
336                }
337
338        if ( did_outfilename )
339                line_directive_out( stdout, 0 );
340
341        skelout();
342        }
343
344
345/* flexend - terminate flex
346 *
347 * note
348 *    This routine does not return.
349 */
350
351void flexend( exit_status )
352int exit_status;
353
354        {
355        int tblsiz;
356        int unlink();
357
358        if ( skelfile != NULL )
359                {
360                if ( ferror( skelfile ) )
361                        lerrsf( _( "input error reading skeleton file %s" ),
362                                skelname );
363
364                else if ( fclose( skelfile ) )
365                        lerrsf( _( "error closing skeleton file %s" ),
366                                skelname );
367                }
368
369        if ( exit_status != 0 && outfile_created )
370                {
371                if ( ferror( stdout ) )
372                        lerrsf( _( "error writing output file %s" ),
373                                outfilename );
374
375                else if ( fclose( stdout ) )
376                        lerrsf( _( "error closing output file %s" ),
377                                outfilename );
378
379                else if ( unlink( outfilename ) )
380                        lerrsf( _( "error deleting output file %s" ),
381                                outfilename );
382                }
383
384        if ( backing_up_report && backing_up_file )
385                {
386                if ( num_backing_up == 0 )
387                        fprintf( backing_up_file, _( "No backing up.\n" ) );
388                else if ( fullspd || fulltbl )
389                        fprintf( backing_up_file,
390                                _( "%d backing up (non-accepting) states.\n" ),
391                                num_backing_up );
392                else
393                        fprintf( backing_up_file,
394                                _( "Compressed tables always back up.\n" ) );
395
396                if ( ferror( backing_up_file ) )
397                        lerrsf( _( "error writing backup file %s" ),
398                                backing_name );
399
400                else if ( fclose( backing_up_file ) )
401                        lerrsf( _( "error closing backup file %s" ),
402                                backing_name );
403                }
404
405        if ( printstats )
406                {
407                fprintf( stderr, _( "%s version %s usage statistics:\n" ),
408                        program_name, flex_version );
409
410                fprintf( stderr, _( "  scanner options: -" ) );
411
412                if ( C_plus_plus )
413                        putc( '+', stderr );
414                if ( backing_up_report )
415                        putc( 'b', stderr );
416                if ( ddebug )
417                        putc( 'd', stderr );
418                if ( caseins )
419                        putc( 'i', stderr );
420                if ( lex_compat )
421                        putc( 'l', stderr );
422                if ( performance_report > 0 )
423                        putc( 'p', stderr );
424                if ( performance_report > 1 )
425                        putc( 'p', stderr );
426                if ( spprdflt )
427                        putc( 's', stderr );
428                if ( use_stdout )
429                        putc( 't', stderr );
430                if ( printstats )
431                        putc( 'v', stderr );    /* always true! */
432                if ( nowarn )
433                        putc( 'w', stderr );
434                if ( interactive == false )
435                        putc( 'B', stderr );
436                if ( interactive == true )
437                        putc( 'I', stderr );
438                if ( ! gen_line_dirs )
439                        putc( 'L', stderr );
440                if ( trace )
441                        putc( 'T', stderr );
442
443                if ( csize == unspecified )
444                        /* We encountered an error fairly early on, so csize
445                         * never got specified.  Define it now, to prevent
446                         * bogus table sizes being written out below.
447                         */
448                        csize = 256;
449
450                if ( csize == 128 )
451                        putc( '7', stderr );
452                else
453                        putc( '8', stderr );
454
455                fprintf( stderr, " -C" );
456
457                if ( long_align )
458                        putc( 'a', stderr );
459                if ( fulltbl )
460                        putc( 'f', stderr );
461                if ( fullspd )
462                        putc( 'F', stderr );
463                if ( useecs )
464                        putc( 'e', stderr );
465                if ( usemecs )
466                        putc( 'm', stderr );
467                if ( use_read )
468                        putc( 'r', stderr );
469
470                if ( did_outfilename )
471                        fprintf( stderr, " -o%s", outfilename );
472
473                if ( skelname )
474                        fprintf( stderr, " -S%s", skelname );
475
476                if ( strcmp( prefix, "yy" ) )
477                        fprintf( stderr, " -P%s", prefix );
478
479                putc( '\n', stderr );
480
481                fprintf( stderr, _( "  %d/%d NFA states\n" ),
482                        lastnfa, current_mns );
483                fprintf( stderr, _( "  %d/%d DFA states (%d words)\n" ),
484                        lastdfa, current_max_dfas, totnst );
485                fprintf( stderr, _( "  %d rules\n" ),
486                num_rules + num_eof_rules - 1 /* - 1 for def. rule */ );
487
488                if ( num_backing_up == 0 )
489                        fprintf( stderr, _( "  No backing up\n" ) );
490                else if ( fullspd || fulltbl )
491                        fprintf( stderr,
492                        _( "  %d backing-up (non-accepting) states\n" ),
493                                num_backing_up );
494                else
495                        fprintf( stderr,
496                                _( "  Compressed tables always back-up\n" ) );
497
498                if ( bol_needed )
499                        fprintf( stderr,
500                                _( "  Beginning-of-line patterns used\n" ) );
501
502                fprintf( stderr, _( "  %d/%d start conditions\n" ), lastsc,
503                        current_max_scs );
504                fprintf( stderr,
505                        _( "  %d epsilon states, %d double epsilon states\n" ),
506                        numeps, eps2 );
507
508                if ( lastccl == 0 )
509                        fprintf( stderr, _( "  no character classes\n" ) );
510                else
511                        fprintf( stderr,
512_( "  %d/%d character classes needed %d/%d words of storage, %d reused\n" ),
513                                lastccl, current_maxccls,
514                                cclmap[lastccl] + ccllen[lastccl],
515                                current_max_ccl_tbl_size, cclreuse );
516
517                fprintf( stderr, _( "  %d state/nextstate pairs created\n" ),
518                        numsnpairs );
519                fprintf( stderr, _( "  %d/%d unique/duplicate transitions\n" ),
520                        numuniq, numdup );
521
522                if ( fulltbl )
523                        {
524                        tblsiz = lastdfa * numecs;
525                        fprintf( stderr, _( "  %d table entries\n" ), tblsiz );
526                        }
527
528                else
529                        {
530                        tblsiz = 2 * (lastdfa + numtemps) + 2 * tblend;
531
532                        fprintf( stderr,
533                                _( "  %d/%d base-def entries created\n" ),
534                                lastdfa + numtemps, current_max_dfas );
535                        fprintf( stderr,
536                        _( "  %d/%d (peak %d) nxt-chk entries created\n" ),
537                                tblend, current_max_xpairs, peakpairs );
538                        fprintf( stderr,
539                _( "  %d/%d (peak %d) template nxt-chk entries created\n" ),
540                                numtemps * nummecs,
541                                current_max_template_xpairs,
542                                numtemps * numecs );
543                        fprintf( stderr, _( "  %d empty table entries\n" ),
544                                nummt );
545                        fprintf( stderr, _( "  %d protos created\n" ),
546                                numprots );
547                        fprintf( stderr,
548                                _( "  %d templates created, %d uses\n" ),
549                                numtemps, tmpuses );
550                        }
551
552                if ( useecs )
553                        {
554                        tblsiz = tblsiz + csize;
555                        fprintf( stderr,
556                                _( "  %d/%d equivalence classes created\n" ),
557                                numecs, csize );
558                        }
559
560                if ( usemecs )
561                        {
562                        tblsiz = tblsiz + numecs;
563                        fprintf( stderr,
564                        _( "  %d/%d meta-equivalence classes created\n" ),
565                                nummecs, csize );
566                        }
567
568                fprintf( stderr,
569                _( "  %d (%d saved) hash collisions, %d DFAs equal\n" ),
570                        hshcol, hshsave, dfaeql );
571                fprintf( stderr, _( "  %d sets of reallocations needed\n" ),
572                        num_reallocs );
573                fprintf( stderr, _( "  %d total table entries needed\n" ),
574                        tblsiz );
575                }
576
577        exit( exit_status );
578        }
579
580
581/* flexinit - initialize flex */
582
583void flexinit( argc, argv )
584int argc;
585char **argv;
586        {
587        int i, sawcmpflag;
588        char *arg;
589
590        printstats = syntaxerror = trace = spprdflt = caseins = false;
591        lex_compat = C_plus_plus = backing_up_report = ddebug = fulltbl = false;
592        fullspd = long_align = nowarn = yymore_used = continued_action = false;
593        do_yylineno = yytext_is_array = in_rule = reject = do_stdinit = false;
594        yymore_really_used = reject_really_used = unspecified;
595        interactive = csize = unspecified;
596        do_yywrap = gen_line_dirs = usemecs = useecs = true;
597        performance_report = 0;
598        did_outfilename = 0;
599        prefix = "yy";
600        yyclass = 0;
601        use_read = use_stdout = false;
602
603        sawcmpflag = false;
604
605        /* Initialize dynamic array for holding the rule actions. */
606        action_size = 2048;     /* default size of action array in bytes */
607        action_array = allocate_character_array( action_size );
608        defs1_offset = prolog_offset = action_offset = action_index = 0;
609        action_array[0] = '\0';
610
611        program_name = argv[0];
612
613        if ( program_name[0] != '\0' &&
614             program_name[strlen( program_name ) - 1] == '+' )
615                C_plus_plus = true;
616
617        /* read flags */
618        for ( --argc, ++argv; argc ; --argc, ++argv )
619                {
620                arg = argv[0];
621
622                if ( arg[0] != '-' || arg[1] == '\0' )
623                        break;
624
625                if ( arg[1] == '-' )
626                        { /* --option */
627                        if ( ! strcmp( arg, "--help" ) )
628                                arg = "-h";
629
630                        else if ( ! strcmp( arg, "--version" ) )
631                                arg = "-V";
632
633                        else if ( ! strcmp( arg, "--" ) )
634                                { /* end of options */
635                                --argc;
636                                ++argv;
637                                break;
638                                }
639                        }
640
641                for ( i = 1; arg[i] != '\0'; ++i )
642                        switch ( arg[i] )
643                                {
644                                case '+':
645                                        C_plus_plus = true;
646                                        break;
647
648                                case 'B':
649                                        interactive = false;
650                                        break;
651
652                                case 'b':
653                                        backing_up_report = true;
654                                        break;
655
656                                case 'c':
657                                        break;
658
659                                case 'C':
660                                        if ( i != 1 )
661                                                flexerror(
662                                _( "-C flag must be given separately" ) );
663
664                                        if ( ! sawcmpflag )
665                                                {
666                                                useecs = false;
667                                                usemecs = false;
668                                                fulltbl = false;
669                                                sawcmpflag = true;
670                                                }
671
672                                        for ( ++i; arg[i] != '\0'; ++i )
673                                                switch ( arg[i] )
674                                                        {
675                                                        case 'a':
676                                                                long_align =
677                                                                        true;
678                                                                break;
679
680                                                        case 'e':
681                                                                useecs = true;
682                                                                break;
683
684                                                        case 'F':
685                                                                fullspd = true;
686                                                                break;
687
688                                                        case 'f':
689                                                                fulltbl = true;
690                                                                break;
691
692                                                        case 'm':
693                                                                usemecs = true;
694                                                                break;
695
696                                                        case 'r':
697                                                                use_read = true;
698                                                                break;
699
700                                                        default:
701                                                                lerrif(
702                                                _( "unknown -C option '%c'" ),
703                                                                (int) arg[i] );
704                                                                break;
705                                                        }
706
707                                        goto get_next_arg;
708
709                                case 'd':
710                                        ddebug = true;
711                                        break;
712
713                                case 'f':
714                                        useecs = usemecs = false;
715                                        use_read = fulltbl = true;
716                                        break;
717
718                                case 'F':
719                                        useecs = usemecs = false;
720                                        use_read = fullspd = true;
721                                        break;
722
723                                case '?':
724                                case 'h':
725                                        usage();
726                                        exit( 0 );
727
728                                case 'I':
729                                        interactive = true;
730                                        break;
731
732                                case 'i':
733                                        caseins = true;
734                                        break;
735
736                                case 'l':
737                                        lex_compat = true;
738                                        break;
739
740                                case 'L':
741                                        gen_line_dirs = false;
742                                        break;
743
744                                case 'n':
745                                        /* Stupid do-nothing deprecated
746                                         * option.
747                                         */
748                                        break;
749
750                                case 'o':
751                                        if ( i != 1 )
752                                                flexerror(
753                                _( "-o flag must be given separately" ) );
754
755                                        outfilename = arg + i + 1;
756                                        did_outfilename = 1;
757                                        goto get_next_arg;
758
759                                case 'P':
760                                        if ( i != 1 )
761                                                flexerror(
762                                _( "-P flag must be given separately" ) );
763
764                                        prefix = arg + i + 1;
765                                        goto get_next_arg;
766
767                                case 'p':
768                                        ++performance_report;
769                                        break;
770
771                                case 'S':
772                                        if ( i != 1 )
773                                                flexerror(
774                                _( "-S flag must be given separately" ) );
775
776                                        skelname = arg + i + 1;
777                                        goto get_next_arg;
778
779                                case 's':
780                                        spprdflt = true;
781                                        break;
782
783                                case 't':
784                                        use_stdout = true;
785                                        break;
786
787                                case 'T':
788                                        trace = true;
789                                        break;
790
791                                case 'v':
792                                        printstats = true;
793                                        break;
794
795                                case 'V':
796                                        printf( _( "%s version %s\n" ),
797                                                program_name, flex_version );
798                                        exit( 0 );
799
800                                case 'w':
801                                        nowarn = true;
802                                        break;
803
804                                case '7':
805                                        csize = 128;
806                                        break;
807
808                                case '8':
809                                        csize = CSIZE;
810                                        break;
811
812                                default:
813                                        fprintf( stderr,
814                _( "%s: unknown flag '%c'.  For usage, try\n\t%s --help\n" ),
815                                                program_name, (int) arg[i],
816                                                program_name );
817                                        exit( 1 );
818                                }
819
820                /* Used by -C, -S, -o, and -P flags in lieu of a "continue 2"
821                 * control.
822                 */
823                get_next_arg: ;
824                }
825
826        num_input_files = argc;
827        input_files = argv;
828        set_input_file( num_input_files > 0 ? input_files[0] : NULL );
829
830        lastccl = lastsc = lastdfa = lastnfa = 0;
831        num_rules = num_eof_rules = default_rule = 0;
832        numas = numsnpairs = tmpuses = 0;
833        numecs = numeps = eps2 = num_reallocs = hshcol = dfaeql = totnst = 0;
834        numuniq = numdup = hshsave = eofseen = datapos = dataline = 0;
835        num_backing_up = onesp = numprots = 0;
836        variable_trailing_context_rules = bol_needed = false;
837
838        out_linenum = linenum = sectnum = 1;
839        firstprot = NIL;
840
841        /* Used in mkprot() so that the first proto goes in slot 1
842         * of the proto queue.
843         */
844        lastprot = 1;
845
846        set_up_initial_allocations();
847        }
848
849
850/* readin - read in the rules section of the input file(s) */
851
852void readin()
853        {
854        static char yy_stdinit[] = "FILE *yyin = stdin, *yyout = stdout;";
855        static char yy_nostdinit[] =
856                "FILE *yyin = (FILE *) 0, *yyout = (FILE *) 0;";
857
858        line_directive_out( (FILE *) 0, 1 );
859
860        if ( yyparse() )
861                {
862                pinpoint_message( _( "fatal parse error" ) );
863                flexend( 1 );
864                }
865
866        if ( syntaxerror )
867                flexend( 1 );
868
869        if ( backing_up_report )
870                {
871                backing_up_file = fopen( backing_name, "w" );
872                if ( backing_up_file == NULL )
873                        lerrsf(
874                        _( "could not create backing-up info file %s" ),
875                                backing_name );
876                }
877
878        else
879                backing_up_file = NULL;
880
881        if ( yymore_really_used == true )
882                yymore_used = true;
883        else if ( yymore_really_used == false )
884                yymore_used = false;
885
886        if ( reject_really_used == true )
887                reject = true;
888        else if ( reject_really_used == false )
889                reject = false;
890
891        if ( performance_report > 0 )
892                {
893                if ( lex_compat )
894                        {
895                        fprintf( stderr,
896_( "-l AT&T lex compatibility option entails a large performance penalty\n" ) );
897                        fprintf( stderr,
898_( " and may be the actual source of other reported performance penalties\n" ) );
899                        }
900
901                else if ( do_yylineno )
902                        {
903                        fprintf( stderr,
904        _( "%%option yylineno entails a large performance penalty\n" ) );
905                        }
906
907                if ( performance_report > 1 )
908                        {
909                        if ( interactive )
910                                fprintf( stderr,
911        _( "-I (interactive) entails a minor performance penalty\n" ) );
912
913                        if ( yymore_used )
914                                fprintf( stderr,
915                _( "yymore() entails a minor performance penalty\n" ) );
916                        }
917
918                if ( reject )
919                        fprintf( stderr,
920                        _( "REJECT entails a large performance penalty\n" ) );
921
922                if ( variable_trailing_context_rules )
923                        fprintf( stderr,
924_( "Variable trailing context rules entail a large performance penalty\n" ) );
925                }
926
927        if ( reject )
928                real_reject = true;
929
930        if ( variable_trailing_context_rules )
931                reject = true;
932
933        if ( (fulltbl || fullspd) && reject )
934                {
935                if ( real_reject )
936                        flexerror(
937                                _( "REJECT cannot be used with -f or -F" ) );
938                else if ( do_yylineno )
939                        flexerror(
940                        _( "%option yylineno cannot be used with -f or -F" ) );
941                else
942                        flexerror(
943        _( "variable trailing context rules cannot be used with -f or -F" ) );
944                }
945
946        if ( reject )
947                outn( "\n#define YY_USES_REJECT" );
948
949        if ( ! do_yywrap )
950                {
951                outn( "\n#define yywrap() 1" );
952                outn( "#define YY_SKIP_YYWRAP" );
953                }
954
955        if ( ddebug )
956                outn( "\n#define FLEX_DEBUG" );
957
958        if ( csize == 256 )
959                outn( "typedef unsigned char YY_CHAR;" );
960        else
961                outn( "typedef char YY_CHAR;" );
962
963        if ( C_plus_plus )
964                {
965                outn( "#define yytext_ptr yytext" );
966
967                if ( interactive )
968                        outn( "#define YY_INTERACTIVE" );
969                }
970
971        else
972                {
973                if ( do_stdinit )
974                        {
975                        outn( "#ifdef VMS" );
976                        outn( "#ifndef __VMS_POSIX" );
977                        outn( yy_nostdinit );
978                        outn( "#else" );
979                        outn( yy_stdinit );
980                        outn( "#endif" );
981                        outn( "#else" );
982                        outn( yy_stdinit );
983                        outn( "#endif" );
984                        }
985
986                else
987                        outn( yy_nostdinit );
988                }
989
990        if ( fullspd )
991                outn( "typedef yyconst struct yy_trans_info *yy_state_type;" );
992        else if ( ! C_plus_plus )
993                outn( "typedef int yy_state_type;" );
994
995        if ( ddebug )
996                outn( "\n#define FLEX_DEBUG" );
997
998        if ( lex_compat )
999                outn( "#define YY_FLEX_LEX_COMPAT" );
1000
1001        if ( do_yylineno && ! C_plus_plus )
1002                {
1003                outn( "extern int yylineno;" );
1004                outn( "int yylineno = 1;" );
1005                }
1006
1007        if ( C_plus_plus )
1008                {
1009                outn( "\n#include <FlexLexer.h>" );
1010
1011                if ( yyclass )
1012                        {
1013                        outn( "int yyFlexLexer::yylex()" );
1014                        outn( "\t{" );
1015                        outn(
1016"\tLexerError( \"yyFlexLexer::yylex invoked but %option yyclass used\" );" );
1017                        outn( "\treturn 0;" );
1018                        outn( "\t}" );
1019       
1020                        out_str( "\n#define YY_DECL int %s::yylex()\n",
1021                                yyclass );
1022                        }
1023                }
1024
1025        else
1026                {
1027                if ( yytext_is_array )
1028                        outn( "extern char yytext[];\n" );
1029
1030                else
1031                        {
1032                        outn( "extern char *yytext;" );
1033                        outn( "#define yytext_ptr yytext" );
1034                        }
1035
1036                if ( yyclass )
1037                        flexerror(
1038                _( "%option yyclass only meaningful for C++ scanners" ) );
1039                }
1040
1041        if ( useecs )
1042                numecs = cre8ecs( nextecm, ecgroup, csize );
1043        else
1044                numecs = csize;
1045
1046        /* Now map the equivalence class for NUL to its expected place. */
1047        ecgroup[0] = ecgroup[csize];
1048        NUL_ec = ABS( ecgroup[0] );
1049
1050        if ( useecs )
1051                ccl2ecl();
1052        }
1053
1054
1055/* set_up_initial_allocations - allocate memory for internal tables */
1056
1057void set_up_initial_allocations()
1058        {
1059        current_mns = INITIAL_MNS;
1060        firstst = allocate_integer_array( current_mns );
1061        lastst = allocate_integer_array( current_mns );
1062        finalst = allocate_integer_array( current_mns );
1063        transchar = allocate_integer_array( current_mns );
1064        trans1 = allocate_integer_array( current_mns );
1065        trans2 = allocate_integer_array( current_mns );
1066        accptnum = allocate_integer_array( current_mns );
1067        assoc_rule = allocate_integer_array( current_mns );
1068        state_type = allocate_integer_array( current_mns );
1069
1070        current_max_rules = INITIAL_MAX_RULES;
1071        rule_type = allocate_integer_array( current_max_rules );
1072        rule_linenum = allocate_integer_array( current_max_rules );
1073        rule_useful = allocate_integer_array( current_max_rules );
1074
1075        current_max_scs = INITIAL_MAX_SCS;
1076        scset = allocate_integer_array( current_max_scs );
1077        scbol = allocate_integer_array( current_max_scs );
1078        scxclu = allocate_integer_array( current_max_scs );
1079        sceof = allocate_integer_array( current_max_scs );
1080        scname = allocate_char_ptr_array( current_max_scs );
1081
1082        current_maxccls = INITIAL_MAX_CCLS;
1083        cclmap = allocate_integer_array( current_maxccls );
1084        ccllen = allocate_integer_array( current_maxccls );
1085        cclng = allocate_integer_array( current_maxccls );
1086
1087        current_max_ccl_tbl_size = INITIAL_MAX_CCL_TBL_SIZE;
1088        ccltbl = allocate_Character_array( current_max_ccl_tbl_size );
1089
1090        current_max_dfa_size = INITIAL_MAX_DFA_SIZE;
1091
1092        current_max_xpairs = INITIAL_MAX_XPAIRS;
1093        nxt = allocate_integer_array( current_max_xpairs );
1094        chk = allocate_integer_array( current_max_xpairs );
1095
1096        current_max_template_xpairs = INITIAL_MAX_TEMPLATE_XPAIRS;
1097        tnxt = allocate_integer_array( current_max_template_xpairs );
1098
1099        current_max_dfas = INITIAL_MAX_DFAS;
1100        base = allocate_integer_array( current_max_dfas );
1101        def = allocate_integer_array( current_max_dfas );
1102        dfasiz = allocate_integer_array( current_max_dfas );
1103        accsiz = allocate_integer_array( current_max_dfas );
1104        dhash = allocate_integer_array( current_max_dfas );
1105        dss = allocate_int_ptr_array( current_max_dfas );
1106        dfaacc = allocate_dfaacc_union( current_max_dfas );
1107
1108        nultrans = (int *) 0;
1109        }
1110
1111
1112void usage()
1113        {
1114        FILE *f = stdout;
1115
1116        fprintf( f,
1117_( "%s [-bcdfhilnpstvwBFILTV78+? -C[aefFmr] -ooutput -Pprefix -Sskeleton]\n" ),
1118                program_name );
1119        fprintf( f, _( "\t[--help --version] [file ...]\n" ) );
1120
1121        fprintf( f, _( "\t-b  generate backing-up information to %s\n" ),
1122                backing_name );
1123        fprintf( f, _( "\t-c  do-nothing POSIX option\n" ) );
1124        fprintf( f, _( "\t-d  turn on debug mode in generated scanner\n" ) );
1125        fprintf( f, _( "\t-f  generate fast, large scanner\n" ) );
1126        fprintf( f, _( "\t-h  produce this help message\n" ) );
1127        fprintf( f, _( "\t-i  generate case-insensitive scanner\n" ) );
1128        fprintf( f, _( "\t-l  maximal compatibility with original lex\n" ) );
1129        fprintf( f, _( "\t-n  do-nothing POSIX option\n" ) );
1130        fprintf( f, _( "\t-p  generate performance report to stderr\n" ) );
1131        fprintf( f,
1132                _( "\t-s  suppress default rule to ECHO unmatched text\n" ) );
1133
1134        if ( ! did_outfilename )
1135                {
1136                sprintf( outfile_path, outfile_template,
1137                        prefix, C_plus_plus ? "cc" : "c" );
1138                outfilename = outfile_path;
1139                }
1140
1141        fprintf( f,
1142                _( "\t-t  write generated scanner on stdout instead of %s\n" ),
1143                outfilename );
1144
1145        fprintf( f,
1146                _( "\t-v  write summary of scanner statistics to f\n" ) );
1147        fprintf( f, _( "\t-w  do not generate warnings\n" ) );
1148        fprintf( f, _( "\t-B  generate batch scanner (opposite of -I)\n" ) );
1149        fprintf( f,
1150                _( "\t-F  use alternative fast scanner representation\n" ) );
1151        fprintf( f,
1152                _( "\t-I  generate interactive scanner (opposite of -B)\n" ) );
1153        fprintf( f, _( "\t-L  suppress #line directives in scanner\n" ) );
1154        fprintf( f, _( "\t-T  %s should run in trace mode\n" ), program_name );
1155        fprintf( f, _( "\t-V  report %s version\n" ), program_name );
1156        fprintf( f, _( "\t-7  generate 7-bit scanner\n" ) );
1157        fprintf( f, _( "\t-8  generate 8-bit scanner\n" ) );
1158        fprintf( f, _( "\t-+  generate C++ scanner class\n" ) );
1159        fprintf( f, _( "\t-?  produce this help message\n" ) );
1160        fprintf( f,
1161_( "\t-C  specify degree of table compression (default is -Cem):\n" ) );
1162        fprintf( f,
1163_( "\t\t-Ca  trade off larger tables for better memory alignment\n" ) );
1164        fprintf( f, _( "\t\t-Ce  construct equivalence classes\n" ) );
1165        fprintf( f,
1166_( "\t\t-Cf  do not compress scanner tables; use -f representation\n" ) );
1167        fprintf( f,
1168_( "\t\t-CF  do not compress scanner tables; use -F representation\n" ) );
1169        fprintf( f, _( "\t\t-Cm  construct meta-equivalence classes\n" ) );
1170        fprintf( f,
1171        _( "\t\t-Cr  use read() instead of stdio for scanner input\n" ) );
1172        fprintf( f, _( "\t-o  specify output filename\n" ) );
1173        fprintf( f, _( "\t-P  specify scanner prefix other than \"yy\"\n" ) );
1174        fprintf( f, _( "\t-S  specify skeleton file\n" ) );
1175        fprintf( f, _( "\t--help     produce this help message\n" ) );
1176        fprintf( f, _( "\t--version  report %s version\n" ), program_name );
1177        }
Note: See TracBrowser for help on using the repository browser.