1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/kconfig/zconf.l Wed Jan 09 18:52:15 2013 +0100
1.3 @@ -0,0 +1,365 @@
1.4 +%option backup nostdinit noyywrap never-interactive full ecs
1.5 +%option 8bit backup nodefault perf-report perf-report
1.6 +%option noinput
1.7 +%x COMMAND HELP STRING PARAM
1.8 +%{
1.9 +/*
1.10 + * Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>
1.11 + * Released under the terms of the GNU GPL v2.0.
1.12 + */
1.13 +
1.14 +#include <limits.h>
1.15 +#include <stdio.h>
1.16 +#include <stdlib.h>
1.17 +#include <string.h>
1.18 +#include <unistd.h>
1.19 +
1.20 +#define LKC_DIRECT_LINK
1.21 +#include "lkc.h"
1.22 +
1.23 +#define START_STRSIZE 16
1.24 +
1.25 +static struct {
1.26 + struct file *file;
1.27 + int lineno;
1.28 +} current_pos;
1.29 +
1.30 +static char *text;
1.31 +static int text_size, text_asize;
1.32 +
1.33 +struct buffer {
1.34 + struct buffer *parent;
1.35 + YY_BUFFER_STATE state;
1.36 +};
1.37 +
1.38 +struct buffer *current_buf;
1.39 +
1.40 +static int last_ts, first_ts;
1.41 +
1.42 +static void zconf_endhelp(void);
1.43 +static void zconf_endfile(void);
1.44 +
1.45 +static void new_string(void)
1.46 +{
1.47 + text = malloc(START_STRSIZE);
1.48 + text_asize = START_STRSIZE;
1.49 + text_size = 0;
1.50 + *text = 0;
1.51 +}
1.52 +
1.53 +static void append_string(const char *str, int size)
1.54 +{
1.55 + int new_size = text_size + size + 1;
1.56 + if (new_size > text_asize) {
1.57 + new_size += START_STRSIZE - 1;
1.58 + new_size &= -START_STRSIZE;
1.59 + text = realloc(text, new_size);
1.60 + text_asize = new_size;
1.61 + }
1.62 + memcpy(text + text_size, str, size);
1.63 + text_size += size;
1.64 + text[text_size] = 0;
1.65 +}
1.66 +
1.67 +static void alloc_string(const char *str, int size)
1.68 +{
1.69 + text = malloc(size + 1);
1.70 + memcpy(text, str, size);
1.71 + text[size] = 0;
1.72 +}
1.73 +%}
1.74 +
1.75 +ws [ \n\t]
1.76 +n [A-Za-z0-9_]
1.77 +
1.78 +%%
1.79 + int str = 0;
1.80 + int ts, i;
1.81 +
1.82 +[ \t]*#.*\n |
1.83 +[ \t]*\n {
1.84 + current_file->lineno++;
1.85 + return T_EOL;
1.86 +}
1.87 +[ \t]*#.*
1.88 +
1.89 +
1.90 +[ \t]+ {
1.91 + BEGIN(COMMAND);
1.92 +}
1.93 +
1.94 +. {
1.95 + unput(yytext[0]);
1.96 + BEGIN(COMMAND);
1.97 +}
1.98 +
1.99 +
1.100 +<COMMAND>{
1.101 + {n}+ {
1.102 + struct kconf_id *id = kconf_id_lookup(yytext, yyleng);
1.103 + BEGIN(PARAM);
1.104 + current_pos.file = current_file;
1.105 + current_pos.lineno = current_file->lineno;
1.106 + if (id && id->flags & TF_COMMAND) {
1.107 + zconflval.id = id;
1.108 + return id->token;
1.109 + }
1.110 + alloc_string(yytext, yyleng);
1.111 + zconflval.string = text;
1.112 + return T_WORD;
1.113 + }
1.114 + .
1.115 + \n {
1.116 + BEGIN(INITIAL);
1.117 + current_file->lineno++;
1.118 + return T_EOL;
1.119 + }
1.120 +}
1.121 +
1.122 +<PARAM>{
1.123 + "&&" return T_AND;
1.124 + "||" return T_OR;
1.125 + "(" return T_OPEN_PAREN;
1.126 + ")" return T_CLOSE_PAREN;
1.127 + "!" return T_NOT;
1.128 + "=" return T_EQUAL;
1.129 + "!=" return T_UNEQUAL;
1.130 + \"|\' {
1.131 + str = yytext[0];
1.132 + new_string();
1.133 + BEGIN(STRING);
1.134 + }
1.135 + \n BEGIN(INITIAL); current_file->lineno++; return T_EOL;
1.136 + --- /* ignore */
1.137 + ({n}|[-/.])+ {
1.138 + struct kconf_id *id = kconf_id_lookup(yytext, yyleng);
1.139 + if (id && id->flags & TF_PARAM) {
1.140 + zconflval.id = id;
1.141 + return id->token;
1.142 + }
1.143 + alloc_string(yytext, yyleng);
1.144 + zconflval.string = text;
1.145 + return T_WORD;
1.146 + }
1.147 + #.* /* comment */
1.148 + \\\n current_file->lineno++;
1.149 + .
1.150 + <<EOF>> {
1.151 + BEGIN(INITIAL);
1.152 + }
1.153 +}
1.154 +
1.155 +<STRING>{
1.156 + [^'"\\\n]+/\n {
1.157 + append_string(yytext, yyleng);
1.158 + zconflval.string = text;
1.159 + return T_WORD_QUOTE;
1.160 + }
1.161 + [^'"\\\n]+ {
1.162 + append_string(yytext, yyleng);
1.163 + }
1.164 + \\.?/\n {
1.165 + append_string(yytext + 1, yyleng - 1);
1.166 + zconflval.string = text;
1.167 + return T_WORD_QUOTE;
1.168 + }
1.169 + \\.? {
1.170 + append_string(yytext + 1, yyleng - 1);
1.171 + }
1.172 + \'|\" {
1.173 + if (str == yytext[0]) {
1.174 + BEGIN(PARAM);
1.175 + zconflval.string = text;
1.176 + return T_WORD_QUOTE;
1.177 + } else
1.178 + append_string(yytext, 1);
1.179 + }
1.180 + \n {
1.181 + printf("%s:%d:warning: multi-line strings not supported\n", zconf_curname(), zconf_lineno());
1.182 + current_file->lineno++;
1.183 + BEGIN(INITIAL);
1.184 + return T_EOL;
1.185 + }
1.186 + <<EOF>> {
1.187 + BEGIN(INITIAL);
1.188 + }
1.189 +}
1.190 +
1.191 +<HELP>{
1.192 + [ \t]+ {
1.193 + ts = 0;
1.194 + for (i = 0; i < yyleng; i++) {
1.195 + if (yytext[i] == '\t')
1.196 + ts = (ts & ~7) + 8;
1.197 + else
1.198 + ts++;
1.199 + }
1.200 + last_ts = ts;
1.201 + if (first_ts) {
1.202 + if (ts < first_ts) {
1.203 + zconf_endhelp();
1.204 + return T_HELPTEXT;
1.205 + }
1.206 + ts -= first_ts;
1.207 + while (ts > 8) {
1.208 + append_string(" ", 8);
1.209 + ts -= 8;
1.210 + }
1.211 + append_string(" ", ts);
1.212 + }
1.213 + }
1.214 + [ \t]*\n/[^ \t\n] {
1.215 + current_file->lineno++;
1.216 + zconf_endhelp();
1.217 + return T_HELPTEXT;
1.218 + }
1.219 + [ \t]*\n {
1.220 + current_file->lineno++;
1.221 + append_string("\n", 1);
1.222 + }
1.223 + [^ \t\n].* {
1.224 + while (yyleng) {
1.225 + if ((yytext[yyleng-1] != ' ') && (yytext[yyleng-1] != '\t'))
1.226 + break;
1.227 + yyleng--;
1.228 + }
1.229 + append_string(yytext, yyleng);
1.230 + if (!first_ts)
1.231 + first_ts = last_ts;
1.232 + }
1.233 + <<EOF>> {
1.234 + zconf_endhelp();
1.235 + return T_HELPTEXT;
1.236 + }
1.237 +}
1.238 +
1.239 +<<EOF>> {
1.240 + if (current_file) {
1.241 + zconf_endfile();
1.242 + return T_EOL;
1.243 + }
1.244 + fclose(yyin);
1.245 + yyterminate();
1.246 +}
1.247 +
1.248 +%%
1.249 +void zconf_starthelp(void)
1.250 +{
1.251 + new_string();
1.252 + last_ts = first_ts = 0;
1.253 + BEGIN(HELP);
1.254 +}
1.255 +
1.256 +static void zconf_endhelp(void)
1.257 +{
1.258 + zconflval.string = text;
1.259 + BEGIN(INITIAL);
1.260 +}
1.261 +
1.262 +
1.263 +/*
1.264 + * Try to open specified file with following names:
1.265 + * ./name
1.266 + * $(srctree)/name
1.267 + * The latter is used when srctree is separate from objtree
1.268 + * when compiling the kernel.
1.269 + * Return NULL if file is not found.
1.270 + */
1.271 +FILE *zconf_fopen(const char *name)
1.272 +{
1.273 + char *env, fullname[PATH_MAX+1];
1.274 + FILE *f;
1.275 +
1.276 + f = fopen(name, "r");
1.277 + if (!f && name != NULL && name[0] != '/') {
1.278 + env = getenv(SRCTREE);
1.279 + if (env) {
1.280 + sprintf(fullname, "%s/%s", env, name);
1.281 + f = fopen(fullname, "r");
1.282 + }
1.283 + }
1.284 + return f;
1.285 +}
1.286 +
1.287 +void zconf_initscan(const char *name)
1.288 +{
1.289 + yyin = zconf_fopen(name);
1.290 + if (!yyin) {
1.291 + printf("can't find file %s\n", name);
1.292 + exit(1);
1.293 + }
1.294 +
1.295 + current_buf = malloc(sizeof(*current_buf));
1.296 + memset(current_buf, 0, sizeof(*current_buf));
1.297 +
1.298 + current_file = file_lookup(name);
1.299 + current_file->lineno = 1;
1.300 +}
1.301 +
1.302 +void zconf_nextfile(const char *name)
1.303 +{
1.304 + struct file *iter;
1.305 + struct file *file = file_lookup(name);
1.306 + struct buffer *buf = malloc(sizeof(*buf));
1.307 + memset(buf, 0, sizeof(*buf));
1.308 +
1.309 + current_buf->state = YY_CURRENT_BUFFER;
1.310 + yyin = zconf_fopen(file->name);
1.311 + if (!yyin) {
1.312 + printf("%s:%d: can't open file \"%s\"\n",
1.313 + zconf_curname(), zconf_lineno(), file->name);
1.314 + exit(1);
1.315 + }
1.316 + yy_switch_to_buffer(yy_create_buffer(yyin, YY_BUF_SIZE));
1.317 + buf->parent = current_buf;
1.318 + current_buf = buf;
1.319 +
1.320 + for (iter = current_file->parent; iter; iter = iter->parent ) {
1.321 + if (!strcmp(current_file->name,iter->name) ) {
1.322 + printf("%s:%d: recursive inclusion detected. "
1.323 + "Inclusion path:\n current file : '%s'\n",
1.324 + zconf_curname(), zconf_lineno(),
1.325 + zconf_curname());
1.326 + iter = current_file->parent;
1.327 + while (iter && \
1.328 + strcmp(iter->name,current_file->name)) {
1.329 + printf(" included from: '%s:%d'\n",
1.330 + iter->name, iter->lineno-1);
1.331 + iter = iter->parent;
1.332 + }
1.333 + if (iter)
1.334 + printf(" included from: '%s:%d'\n",
1.335 + iter->name, iter->lineno+1);
1.336 + exit(1);
1.337 + }
1.338 + }
1.339 + file->lineno = 1;
1.340 + file->parent = current_file;
1.341 + current_file = file;
1.342 +}
1.343 +
1.344 +static void zconf_endfile(void)
1.345 +{
1.346 + struct buffer *parent;
1.347 +
1.348 + current_file = current_file->parent;
1.349 +
1.350 + parent = current_buf->parent;
1.351 + if (parent) {
1.352 + fclose(yyin);
1.353 + yy_delete_buffer(YY_CURRENT_BUFFER);
1.354 + yy_switch_to_buffer(parent->state);
1.355 + }
1.356 + free(current_buf);
1.357 + current_buf = parent;
1.358 +}
1.359 +
1.360 +int zconf_lineno(void)
1.361 +{
1.362 + return current_pos.lineno;
1.363 +}
1.364 +
1.365 +const char *zconf_curname(void)
1.366 +{
1.367 + return current_pos.file ? current_pos.file->name : "<none>";
1.368 +}