source: drbl_ui/backup/test_busybox/busybox-1.7.2/scripts/kconfig/zconf.l @ 200

Last change on this file since 200 was 20, checked in by chris, 17 years ago
File size: 6.1 KB
Line 
1%option backup nostdinit noyywrap never-interactive full ecs
2%option 8bit backup nodefault perf-report perf-report
3%x COMMAND HELP STRING PARAM
4%{
5/*
6 * Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>
7 * Released under the terms of the GNU GPL v2.0.
8 */
9
10#include <limits.h>
11#include <stdio.h>
12#include <stdlib.h>
13#include <string.h>
14#include <unistd.h>
15
16#define LKC_DIRECT_LINK
17#include "lkc.h"
18
19#define START_STRSIZE 16
20
21static struct {
22  struct file *file;
23  int lineno;
24} current_pos;
25
26static char *text;
27static int text_size, text_asize;
28
29struct buffer {
30        struct buffer *parent;
31        YY_BUFFER_STATE state;
32};
33
34struct buffer *current_buf;
35
36static int last_ts, first_ts;
37
38static void zconf_endhelp(void);
39static void zconf_endfile(void);
40
41void new_string(void)
42{
43  text = malloc(START_STRSIZE);
44  text_asize = START_STRSIZE;
45  text_size = 0;
46  *text = 0;
47}
48
49void append_string(const char *str, int size)
50{
51  int new_size = text_size + size + 1;
52  if (new_size > text_asize) {
53    new_size += START_STRSIZE - 1;
54    new_size &= -START_STRSIZE;
55    text = realloc(text, new_size);
56    text_asize = new_size;
57  }
58  memcpy(text + text_size, str, size);
59  text_size += size;
60  text[text_size] = 0;
61}
62
63void alloc_string(const char *str, int size)
64{
65  text = malloc(size + 1);
66  memcpy(text, str, size);
67  text[size] = 0;
68}
69%}
70
71ws  [ \n\t]
72n [A-Za-z0-9_]
73
74%%
75  int str = 0;
76  int ts, i;
77
78[ \t]*#.*\n |
79[ \t]*\n  {
80  current_file->lineno++;
81  return T_EOL;
82}
83[ \t]*#.*
84
85
86[ \t]+  {
87  BEGIN(COMMAND);
88}
89
90. {
91  unput(yytext[0]);
92  BEGIN(COMMAND);
93}
94
95
96<COMMAND>{
97  {n}+  {
98    struct kconf_id *id = kconf_id_lookup(yytext, yyleng);
99    BEGIN(PARAM);
100    current_pos.file = current_file;
101    current_pos.lineno = current_file->lineno;
102    if (id && id->flags & TF_COMMAND) {
103      zconflval.id = id;
104      return id->token;
105    }
106    alloc_string(yytext, yyleng);
107    zconflval.string = text;
108    return T_WORD;
109  }
110  .
111  \n  {
112    BEGIN(INITIAL);
113    current_file->lineno++;
114    return T_EOL;
115  }
116}
117
118<PARAM>{
119  "&&"  return T_AND;
120  "||"  return T_OR;
121  "(" return T_OPEN_PAREN;
122  ")" return T_CLOSE_PAREN;
123  "!" return T_NOT;
124  "=" return T_EQUAL;
125  "!="  return T_UNEQUAL;
126  \"|\' {
127    str = yytext[0];
128    new_string();
129    BEGIN(STRING);
130  }
131  \n  BEGIN(INITIAL); current_file->lineno++; return T_EOL;
132  --- /* ignore */
133  ({n}|[-/.])+  {
134    struct kconf_id *id = kconf_id_lookup(yytext, yyleng);
135    if (id && id->flags & TF_PARAM) {
136      zconflval.id = id;
137      return id->token;
138    }
139    alloc_string(yytext, yyleng);
140    zconflval.string = text;
141    return T_WORD;
142  }
143  #.* /* comment */
144  \\\n  current_file->lineno++;
145  .
146  <<EOF>> {
147    BEGIN(INITIAL);
148  }
149}
150
151<STRING>{
152  [^'"\\\n]+/\n {
153    append_string(yytext, yyleng);
154    zconflval.string = text;
155    return T_WORD_QUOTE;
156  }
157  [^'"\\\n]+  {
158    append_string(yytext, yyleng);
159  }
160  \\.?/\n {
161    append_string(yytext + 1, yyleng - 1);
162    zconflval.string = text;
163    return T_WORD_QUOTE;
164  }
165  \\.?  {
166    append_string(yytext + 1, yyleng - 1);
167  }
168  \'|\" {
169    if (str == yytext[0]) {
170      BEGIN(PARAM);
171      zconflval.string = text;
172      return T_WORD_QUOTE;
173    } else
174      append_string(yytext, 1);
175  }
176  \n  {
177    printf("%s:%d:warning: multi-line strings not supported\n", zconf_curname(), zconf_lineno());
178    current_file->lineno++;
179    BEGIN(INITIAL);
180    return T_EOL;
181  }
182  <<EOF>> {
183    BEGIN(INITIAL);
184  }
185}
186
187<HELP>{
188  [ \t]+  {
189    ts = 0;
190    for (i = 0; i < yyleng; i++) {
191      if (yytext[i] == '\t')
192        ts = (ts & ~7) + 8;
193      else
194        ts++;
195    }
196    last_ts = ts;
197    if (first_ts) {
198      if (ts < first_ts) {
199        zconf_endhelp();
200        return T_HELPTEXT;
201      }
202      ts -= first_ts;
203      while (ts > 8) {
204        append_string("        ", 8);
205        ts -= 8;
206      }
207      append_string("        ", ts);
208    }
209  }
210  [ \t]*\n/[^ \t\n] {
211    current_file->lineno++;
212    zconf_endhelp();
213    return T_HELPTEXT;
214  }
215  [ \t]*\n  {
216    current_file->lineno++;
217    append_string("\n", 1);
218  }
219  [^ \t\n].* {
220    append_string(yytext, yyleng);
221    if (!first_ts)
222      first_ts = last_ts;
223  }
224  <<EOF>> {
225    zconf_endhelp();
226    return T_HELPTEXT;
227  }
228}
229
230<<EOF>> {
231  if (current_file) {
232    zconf_endfile();
233    return T_EOL;
234  }
235  fclose(yyin);
236  yyterminate();
237}
238
239%%
240void zconf_starthelp(void)
241{
242  new_string();
243  last_ts = first_ts = 0;
244  BEGIN(HELP);
245}
246
247static void zconf_endhelp(void)
248{
249  zconflval.string = text;
250  BEGIN(INITIAL);
251}
252
253
254/*
255 * Try to open specified file with following names:
256 * ./name
257 * $(srctree)/name
258 * The latter is used when srctree is separate from objtree
259 * when compiling the kernel.
260 * Return NULL if file is not found.
261 */
262FILE *zconf_fopen(const char *name)
263{
264  char *env, fullname[PATH_MAX+1];
265  FILE *f;
266
267  f = fopen(name, "r");
268  if (!f && name[0] != '/') {
269    env = getenv(SRCTREE);
270    if (env) {
271      sprintf(fullname, "%s/%s", env, name);
272      f = fopen(fullname, "r");
273    }
274  }
275  return f;
276}
277
278void zconf_initscan(const char *name)
279{
280  yyin = zconf_fopen(name);
281  if (!yyin) {
282    printf("can't find file %s\n", name);
283    exit(1);
284  }
285
286  current_buf = malloc(sizeof(*current_buf));
287  memset(current_buf, 0, sizeof(*current_buf));
288
289  current_file = file_lookup(name);
290  current_file->lineno = 1;
291  current_file->flags = FILE_BUSY;
292}
293
294void zconf_nextfile(const char *name)
295{
296  struct file *file = file_lookup(name);
297  struct buffer *buf = malloc(sizeof(*buf));
298  memset(buf, 0, sizeof(*buf));
299
300  current_buf->state = YY_CURRENT_BUFFER;
301  yyin = zconf_fopen(name);
302  if (!yyin) {
303    printf("%s:%d: can't open file \"%s\"\n", zconf_curname(), zconf_lineno(), name);
304    exit(1);
305  }
306  yy_switch_to_buffer(yy_create_buffer(yyin, YY_BUF_SIZE));
307  buf->parent = current_buf;
308  current_buf = buf;
309
310  if (file->flags & FILE_BUSY) {
311    printf("recursive scan (%s)?\n", name);
312    exit(1);
313  }
314  if (file->flags & FILE_SCANNED) {
315    printf("file %s already scanned?\n", name);
316    exit(1);
317  }
318  file->flags |= FILE_BUSY;
319  file->lineno = 1;
320  file->parent = current_file;
321  current_file = file;
322}
323
324static void zconf_endfile(void)
325{
326  struct buffer *parent;
327
328  current_file->flags |= FILE_SCANNED;
329  current_file->flags &= ~FILE_BUSY;
330  current_file = current_file->parent;
331
332  parent = current_buf->parent;
333  if (parent) {
334    fclose(yyin);
335    yy_delete_buffer(YY_CURRENT_BUFFER);
336    yy_switch_to_buffer(parent->state);
337  }
338  free(current_buf);
339  current_buf = parent;
340}
341
342int zconf_lineno(void)
343{
344  return current_pos.lineno;
345}
346
347char *zconf_curname(void)
348{
349  return current_pos.file ? current_pos.file->name : "<none>";
350}
Note: See TracBrowser for help on using the repository browser.