Updated WIN32 code specific sections. Changed header.
[idzebra-moved-to-github.git] / dfa / readfile.c
1 /*
2  * Copyright (C) 1994-1999, Index Data
3  * All rights reserved.
4  * Sebastian Hammer, Adam Dickmeiss
5  *
6  * $Log: readfile.c,v $
7  * Revision 1.8  1999-02-02 14:50:12  adam
8  * Updated WIN32 code specific sections. Changed header.
9  *
10  * Revision 1.7  1996/10/29 13:57:28  adam
11  * Include of zebrautl.h instead of alexutil.h.
12  *
13  * Revision 1.6  1996/01/08 09:09:21  adam
14  * Function dfa_parse got 'const' string argument.
15  * New functions to define char mappings made public.
16  *
17  * Revision 1.5  1995/09/04  12:33:27  adam
18  * Various cleanup. YAZ util used instead.
19  *
20  * Revision 1.4  1995/01/25  11:30:51  adam
21  * Simple error reporting when parsing regular expressions.
22  * Memory usage reduced.
23  *
24  * Revision 1.3  1995/01/24  16:00:22  adam
25  * Added -ansi to CFLAGS.
26  * Some changes to the dfa module.
27  *
28  * Revision 1.2  1994/09/26  16:30:57  adam
29  * Minor changes. imalloc uses xmalloc now.
30  *
31  * Revision 1.1  1994/09/26  10:16:56  adam
32  * First version of dfa module in alex. This version uses yacc to parse
33  * regular expressions. This should be hand-made instead.
34  *
35  */
36 #include <stdio.h>
37 #include <assert.h>
38
39 #include <stdlib.h>
40 #include <string.h>
41 #include <ctype.h>
42
43 #include <zebrautl.h>
44 #include <dfa.h>
45 #include "lexer.h"
46
47 #define MAXLINE 512
48
49 static FILE *inf;
50 static FILE *outf;
51 static const char *inf_name;
52 static int line_no;
53 static int err_no;
54
55 static void
56     prep        (char **s),
57     read_defs   (void),
58     read_rules  (struct DFA *dfap),
59     read_tail   (void);
60
61 static char
62     *read_line  (void);
63
64 static void prep (char **s)
65 {
66     static char expr_buf[MAXLINE+1];
67     char *dst = expr_buf;
68     const char *src = *s;
69     int c;
70
71     while ((c = *src++))
72         *dst++ = c;
73
74     *dst = '\0';
75     *s = expr_buf;
76 }
77
78 static char *read_line (void)
79 {
80     static char linebuf[MAXLINE+1];
81     ++line_no;
82     return fgets (linebuf, MAXLINE, inf);
83 }
84
85 static void read_defs (void)
86 {
87     const char *s;
88     while ((s=read_line()))
89     {
90         if (*s == '%' && s[1] == '%')
91             return;
92         else if (*s == '\0' || isspace (*s))
93             fputs (s, outf);
94     }
95     error ("missing rule section");
96 }
97
98 static void read_rules (struct DFA *dfa)
99 {
100     char *s;
101     const char *sc;
102     int i;
103     int no = 0;
104
105     fputs ("\n#ifndef YY_BREAK\n#define YY_BREAK break;\n#endif\n", outf);
106     fputs ("void lexact (int no)\n{\n", outf);
107     fputs (  "\tswitch (no)\n\t{\n", outf);
108     while ((s=read_line()))
109     {
110         if (*s == '%' && s[1] == '%')
111             break;
112         else if (*s == '\0' || isspace (*s))
113             /* copy rest of line to output */
114             fputs (s, outf);
115         else
116         { 
117             /* preprocess regular expression */
118             prep (&s);                   
119             /* now parse regular expression */
120             sc = s;
121             i = dfa_parse (dfa, &sc);
122             if (i)
123             {
124                 fprintf (stderr, "%s #%d: regular expression syntax error\n",
125                         inf_name, line_no);
126                 assert (0);
127                 err_no++;
128             }
129             else
130             {
131                 if (no)
132                     fputs ("\t\tYY_BREAK\n", outf);
133                 no++;
134                 fprintf (outf, "\tcase %d:\n#line %d\n\t\t", no, line_no);
135             }
136             while (*sc == '\t' || *sc == ' ')
137                 sc++;
138             fputs (sc, outf);
139         }
140     }
141     fputs ("\tYY_BREAK\n\t}\n}\n", outf);
142     if (!no)
143         error ("no regular expressions in rule section");
144 }
145
146 static void read_tail (void)
147 {
148     const char *s;
149     while ((s=read_line()))
150         fputs (s, outf);
151 }
152
153 int read_file (const char *s, struct DFA *dfa)
154 {
155     inf_name = s;
156     if (!(inf=fopen (s,"r")))
157     {
158         error ("cannot open `%s'", s);
159         return -1;
160     }
161
162     if (!(outf=fopen ("lex.yy.c", "w")))
163     {
164         error ("cannot open `%s'", "lex.yy.c");
165         return -2;
166     }
167
168     line_no = 0;
169     err_no = 0;
170
171     read_defs ();
172     read_rules (dfa);
173     read_tail ();
174
175     fclose (outf);
176     fclose (inf);
177     return err_no;
178 }