1 %{
2 /* $Id: configfile.l 10305 2018-12-02 14:21:56Z iulius $
3 **
4 ** A flex input file for the innfeed config file.
5 **
6 ** Written by James Brister <brister@vix.com>
7 */
8
9 #include "innfeed.h"
10
11 #include <errno.h>
12 #include <stdlib.h>
13 #include <string.h>
14 #include <syslog.h>
15
16 #include "inn/libinn.h"
17
18 #include "configfile.h"
19 #include "config_y.h"
20 #include "misc.h"
21
22 #if ! defined (FLEX_SCANNER)
23 #error "You must use FLEX to process the lex input file."
24 #endif
25
26 /* Some versions of flex (such as 2.6.1-1.3 in Debian stretch) declare a
27 variable as int that should be size_t. We can't really do much about
28 that, and it's fixed in current flex, so just suppress the warning.
29 Same thing for a possible NULL pointer dereference. */
30 #pragma GCC diagnostic ignored "-Wsign-compare"
31 #pragma GCC diagnostic ignored "-Wnull-dereference"
32
33 #if defined (FLEX_DEBUG)
34 #define YY_USER_INIT yy_flex_debug = (getenv ("YYDEBUG") == NULL ? 0 : 1)
35 #endif
36
37 /* We never use this function but flex always defines it, so silence the
38 warnings about it. */
39 static void yyunput(int, char *) UNUSED;
40
41 char *strPtr = 0 ;
42 int strPtrLen = 0 ;
43 int strIdx = 0 ;
44 int sawBsl ;
45 int lineCount = 0 ;
46 int current ;
47
strAppend(int ch)48 static void strAppend (int ch)
49 {
50 if (strIdx == strPtrLen)
51 {
52 if (strPtr == 0)
53 strPtr = xmalloc (strPtrLen = 50) ;
54 else
55 strPtr = xrealloc (strPtr,strPtrLen += 10) ;
56 }
57 strPtr [strIdx++] = ch ;
58 }
59
60 #define MAX_INCLUDE_DEPTH 11
61 struct includeFile {
62 YY_BUFFER_STATE state;
63 char *name ;
64 } include_stack[MAX_INCLUDE_DEPTH];
65 int include_stack_ptr = 0;
66
67 %}
68
69 %x incl
70
71 ID [a-zA-Z][-a-zA-Z0-9._/]+
72
73 %%
74
75 \n lineCount++ ;
76
77 ":" { return (COLON) ; }
78
79 "{" { return (LBRACE) ; }
80
81 "}" { return (RBRACE) ; }
82
83 [pP][eE][eE][rR] { return (PEER) ; }
84
85 ^"$INCLUDE" BEGIN(incl);
86
87 <incl>[ \t]* /* eat the whitespace before include filename */
88
89 <incl>[^ \t\n]+ {
90 if (include_stack_ptr == MAX_INCLUDE_DEPTH - 1)
91 {
92 int i ;
93 fprintf( stderr, "Includes nested too deeply:\n" );
94 for (i = 1 ; i <= include_stack_ptr ; i++)
95 fprintf (stderr,"\t%s\n",include_stack[i].name) ;
96
97 syslog (LOG_ERR, "includes nested to deeply") ;
98 exit( 1 );
99 }
100
101 if ((yyin = fopen(yytext,"r")) == NULL)
102 {
103 syslog (LOG_CRIT,"include file fopen failed: %s %s",
104 yytext,strerror(errno));
105 fprintf (stderr,"include file fopen failed: %s %s\n",
106 yytext,strerror(errno));
107 exit (1) ;
108 }
109 else
110 {
111 d_printf (1,"Including (%d) from %s\n",
112 include_stack_ptr + 1,yytext) ;
113 include_stack[include_stack_ptr].state = YY_CURRENT_BUFFER;
114 include_stack[++include_stack_ptr].name = xstrdup (yytext) ;
115 yy_switch_to_buffer(yy_create_buffer(yyin, YY_BUF_SIZE));
116 }
117
118 BEGIN(INITIAL);
119 }
120
121 <<EOF>> {
122 if ( include_stack_ptr <= 0 )
123 yyterminate();
124 else
125 {
126 free (include_stack[include_stack_ptr].name) ;
127 yy_delete_buffer(YY_CURRENT_BUFFER);
128 yy_switch_to_buffer(include_stack[--include_stack_ptr].state);
129 }
130 }
131
132 [gG][rR][oO][uU][pP] { return (GROUP) ; }
133
134 #[^\n]* { (void) 0 ; }
135
136 [ \t]+ { (void) 1 ; }
137
138 '\\[\\abfnrtv]' {
139 switch (yytext[2]) {
140 case '\\': yylval.chr = '\\' ; break ;
141 case 'a': yylval.chr = 007 ; break ;
142 case 'b': yylval.chr = 010 ; break ;
143 case 'f': yylval.chr = 014 ; break ;
144 case 'n': yylval.chr = 012 ; break ;
145 case 'r': yylval.chr = 015 ; break ;
146 case 't': yylval.chr = 011 ; break ;
147 case 'v': yylval.chr = 013 ; break ;
148 }
149 return (CHAR) ; }
150
151 '.' { yylval.chr = yytext[1] ; return (CHAR) ; }
152
153 '\\[0-9][0-9][0-9]' { yylval.chr = (char)strtol(&yytext[2], (char **)NULL, 8);
154 return (CHAR) ;}
155
156 \"[^\"]* {{
157 size_t i ;
158
159 for (i = 1, strIdx = 0, sawBsl = 0 ; ; i++)
160 {
161 /* Cast yyleng to size_t because it used to be an int
162 * in flex versions anterior or equal to 2.5.35.
163 * Do not use yyget_leng() here because old flex versions
164 * do not define it. */
165 if (i < (size_t) yyleng)
166 current = yytext [i] ;
167 else
168 current = input() ;
169
170 if (current != EOF)
171 {
172 switch (current)
173 {
174 case '\\':
175 if (sawBsl)
176 {
177 strAppend (current) ;
178 sawBsl = 0 ;
179 }
180 else
181 sawBsl = 1 ;
182 break ;
183
184 case '\n':
185 if (!sawBsl)
186 strAppend(current) ;
187 sawBsl = 0 ;
188 lineCount++ ;
189 break ;
190
191 case '\"':
192 if (sawBsl)
193 {
194 strAppend (current) ;
195 sawBsl = 0 ;
196 }
197 else
198 {
199 strAppend ('\0') ;
200 yylval.string = strPtr ;
201 strPtr = 0 ;
202 strPtrLen = strIdx = 0 ;
203 return (XSTRING) ;
204 }
205 break ;
206
207 case 'a':
208 case 'b':
209 case 'f':
210 case 'n':
211 case 'r':
212 case 't':
213 case 'v':
214 if (sawBsl)
215 {
216 switch (current)
217 {
218 case 'a': strAppend (007) ; break ;
219 case 'b': strAppend (010) ; break ;
220 case 'f': strAppend (014) ; break ;
221 case 'n': strAppend (012) ; break ;
222 case 'r': strAppend (015) ; break ;
223 case 't': strAppend (011) ; break ;
224 case 'v': strAppend (013) ; break ;
225 }
226 sawBsl = 0 ;
227 }
228 else
229 strAppend (current) ;
230 break ;
231
232 default:
233 strAppend (current) ;
234 sawBsl = 0 ;
235 break ;
236 }
237 }
238 else
239 {
240 return (XSTRING) ;
241 }
242 }
243 }}
244
245 [-0-9][0-9]* { yylval.integer = atoi (yytext) ; return (IVAL) ; }
246
247 [-0-9][0-9]*\.[0-9]* { yylval.real = atof (yytext) ; return (RVAL) ; }
248
249 [^#:\'\" \t\n]+ {
250 yylval.name = xstrdup (yytext) ;
251 if (strcasecmp (yylval.name,"false") == 0)
252 return (FALSEBVAL) ;
253 else if (strcasecmp (yylval.name,"true") == 0)
254 return (TRUEBVAL) ;
255 else
256 return (WORD) ;
257 }
258
259 %%
260
261
262
263