2011-06-07 21:34:05 +04:00
|
|
|
%option nostdinit noyywrap never-interactive full ecs
|
2018-03-22 20:00:14 +03:00
|
|
|
%option 8bit nodefault yylineno
|
kconfig: support user-defined function and recursively expanded variable
Now, we got a basic ability to test compiler capability in Kconfig.
config CC_HAS_STACKPROTECTOR
def_bool $(shell,($(CC) -Werror -fstack-protector -E -x c /dev/null -o /dev/null 2>/dev/null) && echo y || echo n)
This works, but it is ugly to repeat this long boilerplate.
We want to describe like this:
config CC_HAS_STACKPROTECTOR
bool
default $(cc-option,-fstack-protector)
It is straight-forward to add a new function, but I do not like to
hard-code specialized functions like that. Hence, here is another
feature, user-defined function. This works as a textual shorthand
with parameterization.
A user-defined function is defined by using the = operator, and can
be referenced in the same way as built-in functions. A user-defined
function in Make is referenced like $(call my-func,arg1,arg2), but I
omitted the 'call' to make the syntax shorter.
The definition of a user-defined function contains $(1), $(2), etc.
in its body to reference the parameters. It is grammatically valid
to pass more or fewer arguments when calling it. We already exploit
this feature in our makefiles; scripts/Kbuild.include defines cc-option
which takes two arguments at most, but most of the callers pass only
one argument.
By the way, a variable is supported as a subset of this feature since
a variable is "a user-defined function with zero argument". In this
context, I mean "variable" as recursively expanded variable. I will
add a different flavored variable in the next commit.
The code above can be written as follows:
[Example Code]
success = $(shell,($(1)) >/dev/null 2>&1 && echo y || echo n)
cc-option = $(success,$(CC) -Werror $(1) -E -x c /dev/null -o /dev/null)
config CC_HAS_STACKPROTECTOR
def_bool $(cc-option,-fstack-protector)
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_CC_HAS_STACKPROTECTOR=y
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
2018-05-28 12:21:49 +03:00
|
|
|
%x COMMAND HELP STRING PARAM ASSIGN_VAL
|
2005-04-17 02:20:36 +04:00
|
|
|
%{
|
|
|
|
/*
|
|
|
|
* Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>
|
|
|
|
* Released under the terms of the GNU GPL v2.0.
|
|
|
|
*/
|
|
|
|
|
kconfig: support user-defined function and recursively expanded variable
Now, we got a basic ability to test compiler capability in Kconfig.
config CC_HAS_STACKPROTECTOR
def_bool $(shell,($(CC) -Werror -fstack-protector -E -x c /dev/null -o /dev/null 2>/dev/null) && echo y || echo n)
This works, but it is ugly to repeat this long boilerplate.
We want to describe like this:
config CC_HAS_STACKPROTECTOR
bool
default $(cc-option,-fstack-protector)
It is straight-forward to add a new function, but I do not like to
hard-code specialized functions like that. Hence, here is another
feature, user-defined function. This works as a textual shorthand
with parameterization.
A user-defined function is defined by using the = operator, and can
be referenced in the same way as built-in functions. A user-defined
function in Make is referenced like $(call my-func,arg1,arg2), but I
omitted the 'call' to make the syntax shorter.
The definition of a user-defined function contains $(1), $(2), etc.
in its body to reference the parameters. It is grammatically valid
to pass more or fewer arguments when calling it. We already exploit
this feature in our makefiles; scripts/Kbuild.include defines cc-option
which takes two arguments at most, but most of the callers pass only
one argument.
By the way, a variable is supported as a subset of this feature since
a variable is "a user-defined function with zero argument". In this
context, I mean "variable" as recursively expanded variable. I will
add a different flavored variable in the next commit.
The code above can be written as follows:
[Example Code]
success = $(shell,($(1)) >/dev/null 2>&1 && echo y || echo n)
cc-option = $(success,$(CC) -Werror $(1) -E -x c /dev/null -o /dev/null)
config CC_HAS_STACKPROTECTOR
def_bool $(cc-option,-fstack-protector)
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_CC_HAS_STACKPROTECTOR=y
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
2018-05-28 12:21:49 +03:00
|
|
|
#include <assert.h>
|
2005-04-17 02:20:36 +04:00
|
|
|
#include <limits.h>
|
|
|
|
#include <stdio.h>
|
|
|
|
#include <stdlib.h>
|
|
|
|
#include <string.h>
|
|
|
|
#include <unistd.h>
|
|
|
|
|
|
|
|
#include "lkc.h"
|
|
|
|
|
|
|
|
#define START_STRSIZE 16
|
|
|
|
|
2005-11-09 08:34:53 +03:00
|
|
|
static struct {
|
|
|
|
struct file *file;
|
|
|
|
int lineno;
|
|
|
|
} current_pos;
|
|
|
|
|
2005-11-09 08:34:51 +03:00
|
|
|
static char *text;
|
2005-04-17 02:20:36 +04:00
|
|
|
static int text_size, text_asize;
|
|
|
|
|
|
|
|
struct buffer {
|
2014-06-10 14:08:13 +04:00
|
|
|
struct buffer *parent;
|
|
|
|
YY_BUFFER_STATE state;
|
2005-04-17 02:20:36 +04:00
|
|
|
};
|
|
|
|
|
|
|
|
struct buffer *current_buf;
|
|
|
|
|
|
|
|
static int last_ts, first_ts;
|
|
|
|
|
kconfig: reference environment variables directly and remove 'option env='
To get access to environment variables, Kconfig needs to define a
symbol using "option env=" syntax. It is tedious to add a symbol entry
for each environment variable given that we need to define much more
such as 'CC', 'AS', 'srctree' etc. to evaluate the compiler capability
in Kconfig.
Adding '$' for symbol references is grammatically inconsistent.
Looking at the code, the symbols prefixed with 'S' are expanded by:
- conf_expand_value()
This is used to expand 'arch/$ARCH/defconfig' and 'defconfig_list'
- sym_expand_string_value()
This is used to expand strings in 'source' and 'mainmenu'
All of them are fixed values independent of user configuration. So,
they can be changed into the direct expansion instead of symbols.
This change makes the code much cleaner. The bounce symbols 'SRCARCH',
'ARCH', 'SUBARCH', 'KERNELVERSION' are gone.
sym_init() hard-coding 'UNAME_RELEASE' is also gone. 'UNAME_RELEASE'
should be replaced with an environment variable.
ARCH_DEFCONFIG is a normal symbol, so it should be simply referenced
without '$' prefix.
The new syntax is addicted by Make. The variable reference needs
parentheses, like $(FOO), but you can omit them for single-letter
variables, like $F. Yet, in Makefiles, people tend to use the
parenthetical form for consistency / clarification.
At this moment, only the environment variable is supported, but I will
extend the concept of 'variable' later on.
The variables are expanded in the lexer so we can simplify the token
handling on the parser side.
For example, the following code works.
[Example code]
config MY_TOOLCHAIN_LIST
string
default "My tools: CC=$(CC), AS=$(AS), CPP=$(CPP)"
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_MY_TOOLCHAIN_LIST="My tools: CC=gcc, AS=as, CPP=gcc -E"
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
Reviewed-by: Kees Cook <keescook@chromium.org>
2018-05-28 12:21:40 +03:00
|
|
|
static char *expand_token(const char *in, size_t n);
|
|
|
|
static void append_expanded_string(const char *in);
|
2005-04-17 02:20:36 +04:00
|
|
|
static void zconf_endhelp(void);
|
2005-11-09 08:34:53 +03:00
|
|
|
static void zconf_endfile(void);
|
2005-04-17 02:20:36 +04:00
|
|
|
|
2009-10-15 23:13:36 +04:00
|
|
|
static void new_string(void)
|
2005-04-17 02:20:36 +04:00
|
|
|
{
|
2012-11-06 18:32:08 +04:00
|
|
|
text = xmalloc(START_STRSIZE);
|
2005-04-17 02:20:36 +04:00
|
|
|
text_asize = START_STRSIZE;
|
|
|
|
text_size = 0;
|
2005-11-09 08:34:51 +03:00
|
|
|
*text = 0;
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|
|
|
|
|
2009-10-15 23:13:36 +04:00
|
|
|
static void append_string(const char *str, int size)
|
2005-04-17 02:20:36 +04:00
|
|
|
{
|
|
|
|
int new_size = text_size + size + 1;
|
|
|
|
if (new_size > text_asize) {
|
2005-11-09 08:34:51 +03:00
|
|
|
new_size += START_STRSIZE - 1;
|
|
|
|
new_size &= -START_STRSIZE;
|
2018-02-08 19:19:07 +03:00
|
|
|
text = xrealloc(text, new_size);
|
2005-04-17 02:20:36 +04:00
|
|
|
text_asize = new_size;
|
|
|
|
}
|
2005-11-09 08:34:51 +03:00
|
|
|
memcpy(text + text_size, str, size);
|
2005-04-17 02:20:36 +04:00
|
|
|
text_size += size;
|
2005-11-09 08:34:51 +03:00
|
|
|
text[text_size] = 0;
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|
|
|
|
|
2009-10-15 23:13:36 +04:00
|
|
|
static void alloc_string(const char *str, int size)
|
2005-04-17 02:20:36 +04:00
|
|
|
{
|
2012-11-06 18:32:08 +04:00
|
|
|
text = xmalloc(size + 1);
|
2005-04-17 02:20:36 +04:00
|
|
|
memcpy(text, str, size);
|
|
|
|
text[size] = 0;
|
|
|
|
}
|
2015-07-12 10:41:50 +03:00
|
|
|
|
|
|
|
static void warn_ignored_character(char chr)
|
|
|
|
{
|
|
|
|
fprintf(stderr,
|
|
|
|
"%s:%d:warning: ignoring unsupported character '%c'\n",
|
|
|
|
zconf_curname(), zconf_lineno(), chr);
|
|
|
|
}
|
2005-04-17 02:20:36 +04:00
|
|
|
%}
|
|
|
|
|
2015-07-12 10:41:50 +03:00
|
|
|
n [A-Za-z0-9_-]
|
2005-04-17 02:20:36 +04:00
|
|
|
|
|
|
|
%%
|
|
|
|
int str = 0;
|
|
|
|
int ts, i;
|
|
|
|
|
2005-11-09 08:34:53 +03:00
|
|
|
[ \t]*#.*\n |
|
|
|
|
[ \t]*\n {
|
|
|
|
return T_EOL;
|
|
|
|
}
|
2005-04-17 02:20:36 +04:00
|
|
|
[ \t]*#.*
|
|
|
|
|
|
|
|
|
|
|
|
[ \t]+ {
|
|
|
|
BEGIN(COMMAND);
|
|
|
|
}
|
|
|
|
|
|
|
|
. {
|
|
|
|
unput(yytext[0]);
|
|
|
|
BEGIN(COMMAND);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
<COMMAND>{
|
|
|
|
{n}+ {
|
2011-05-05 05:14:44 +04:00
|
|
|
const struct kconf_id *id = kconf_id_lookup(yytext, yyleng);
|
2005-11-09 08:34:53 +03:00
|
|
|
current_pos.file = current_file;
|
2018-03-22 20:00:14 +03:00
|
|
|
current_pos.lineno = yylineno;
|
2005-11-09 08:34:51 +03:00
|
|
|
if (id && id->flags & TF_COMMAND) {
|
2018-05-28 12:21:48 +03:00
|
|
|
BEGIN(PARAM);
|
2018-01-11 18:50:50 +03:00
|
|
|
yylval.id = id;
|
2005-11-09 08:34:51 +03:00
|
|
|
return id->token;
|
|
|
|
}
|
2005-04-17 02:20:36 +04:00
|
|
|
alloc_string(yytext, yyleng);
|
2018-01-11 18:50:50 +03:00
|
|
|
yylval.string = text;
|
kconfig: support user-defined function and recursively expanded variable
Now, we got a basic ability to test compiler capability in Kconfig.
config CC_HAS_STACKPROTECTOR
def_bool $(shell,($(CC) -Werror -fstack-protector -E -x c /dev/null -o /dev/null 2>/dev/null) && echo y || echo n)
This works, but it is ugly to repeat this long boilerplate.
We want to describe like this:
config CC_HAS_STACKPROTECTOR
bool
default $(cc-option,-fstack-protector)
It is straight-forward to add a new function, but I do not like to
hard-code specialized functions like that. Hence, here is another
feature, user-defined function. This works as a textual shorthand
with parameterization.
A user-defined function is defined by using the = operator, and can
be referenced in the same way as built-in functions. A user-defined
function in Make is referenced like $(call my-func,arg1,arg2), but I
omitted the 'call' to make the syntax shorter.
The definition of a user-defined function contains $(1), $(2), etc.
in its body to reference the parameters. It is grammatically valid
to pass more or fewer arguments when calling it. We already exploit
this feature in our makefiles; scripts/Kbuild.include defines cc-option
which takes two arguments at most, but most of the callers pass only
one argument.
By the way, a variable is supported as a subset of this feature since
a variable is "a user-defined function with zero argument". In this
context, I mean "variable" as recursively expanded variable. I will
add a different flavored variable in the next commit.
The code above can be written as follows:
[Example Code]
success = $(shell,($(1)) >/dev/null 2>&1 && echo y || echo n)
cc-option = $(success,$(CC) -Werror $(1) -E -x c /dev/null -o /dev/null)
config CC_HAS_STACKPROTECTOR
def_bool $(cc-option,-fstack-protector)
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_CC_HAS_STACKPROTECTOR=y
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
2018-05-28 12:21:49 +03:00
|
|
|
return T_VARIABLE;
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|
2018-05-28 12:21:52 +03:00
|
|
|
({n}|$)+ {
|
|
|
|
/* this token includes at least one '$' */
|
|
|
|
yylval.string = expand_token(yytext, yyleng);
|
|
|
|
if (strlen(yylval.string))
|
|
|
|
return T_VARIABLE;
|
|
|
|
free(yylval.string);
|
|
|
|
}
|
2018-05-28 12:21:50 +03:00
|
|
|
"=" { BEGIN(ASSIGN_VAL); yylval.flavor = VAR_RECURSIVE; return T_ASSIGN; }
|
|
|
|
":=" { BEGIN(ASSIGN_VAL); yylval.flavor = VAR_SIMPLE; return T_ASSIGN; }
|
2018-05-28 12:21:51 +03:00
|
|
|
"+=" { BEGIN(ASSIGN_VAL); yylval.flavor = VAR_APPEND; return T_ASSIGN; }
|
kconfig: support user-defined function and recursively expanded variable
Now, we got a basic ability to test compiler capability in Kconfig.
config CC_HAS_STACKPROTECTOR
def_bool $(shell,($(CC) -Werror -fstack-protector -E -x c /dev/null -o /dev/null 2>/dev/null) && echo y || echo n)
This works, but it is ugly to repeat this long boilerplate.
We want to describe like this:
config CC_HAS_STACKPROTECTOR
bool
default $(cc-option,-fstack-protector)
It is straight-forward to add a new function, but I do not like to
hard-code specialized functions like that. Hence, here is another
feature, user-defined function. This works as a textual shorthand
with parameterization.
A user-defined function is defined by using the = operator, and can
be referenced in the same way as built-in functions. A user-defined
function in Make is referenced like $(call my-func,arg1,arg2), but I
omitted the 'call' to make the syntax shorter.
The definition of a user-defined function contains $(1), $(2), etc.
in its body to reference the parameters. It is grammatically valid
to pass more or fewer arguments when calling it. We already exploit
this feature in our makefiles; scripts/Kbuild.include defines cc-option
which takes two arguments at most, but most of the callers pass only
one argument.
By the way, a variable is supported as a subset of this feature since
a variable is "a user-defined function with zero argument". In this
context, I mean "variable" as recursively expanded variable. I will
add a different flavored variable in the next commit.
The code above can be written as follows:
[Example Code]
success = $(shell,($(1)) >/dev/null 2>&1 && echo y || echo n)
cc-option = $(success,$(CC) -Werror $(1) -E -x c /dev/null -o /dev/null)
config CC_HAS_STACKPROTECTOR
def_bool $(cc-option,-fstack-protector)
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_CC_HAS_STACKPROTECTOR=y
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
2018-05-28 12:21:49 +03:00
|
|
|
[[:blank:]]+
|
2015-07-12 10:41:50 +03:00
|
|
|
. warn_ignored_character(*yytext);
|
2005-11-09 08:34:53 +03:00
|
|
|
\n {
|
|
|
|
BEGIN(INITIAL);
|
|
|
|
return T_EOL;
|
|
|
|
}
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|
|
|
|
|
kconfig: support user-defined function and recursively expanded variable
Now, we got a basic ability to test compiler capability in Kconfig.
config CC_HAS_STACKPROTECTOR
def_bool $(shell,($(CC) -Werror -fstack-protector -E -x c /dev/null -o /dev/null 2>/dev/null) && echo y || echo n)
This works, but it is ugly to repeat this long boilerplate.
We want to describe like this:
config CC_HAS_STACKPROTECTOR
bool
default $(cc-option,-fstack-protector)
It is straight-forward to add a new function, but I do not like to
hard-code specialized functions like that. Hence, here is another
feature, user-defined function. This works as a textual shorthand
with parameterization.
A user-defined function is defined by using the = operator, and can
be referenced in the same way as built-in functions. A user-defined
function in Make is referenced like $(call my-func,arg1,arg2), but I
omitted the 'call' to make the syntax shorter.
The definition of a user-defined function contains $(1), $(2), etc.
in its body to reference the parameters. It is grammatically valid
to pass more or fewer arguments when calling it. We already exploit
this feature in our makefiles; scripts/Kbuild.include defines cc-option
which takes two arguments at most, but most of the callers pass only
one argument.
By the way, a variable is supported as a subset of this feature since
a variable is "a user-defined function with zero argument". In this
context, I mean "variable" as recursively expanded variable. I will
add a different flavored variable in the next commit.
The code above can be written as follows:
[Example Code]
success = $(shell,($(1)) >/dev/null 2>&1 && echo y || echo n)
cc-option = $(success,$(CC) -Werror $(1) -E -x c /dev/null -o /dev/null)
config CC_HAS_STACKPROTECTOR
def_bool $(cc-option,-fstack-protector)
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_CC_HAS_STACKPROTECTOR=y
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
2018-05-28 12:21:49 +03:00
|
|
|
<ASSIGN_VAL>{
|
|
|
|
[^[:blank:]\n]+.* {
|
|
|
|
alloc_string(yytext, yyleng);
|
|
|
|
yylval.string = text;
|
|
|
|
return T_ASSIGN_VAL;
|
|
|
|
}
|
|
|
|
\n { BEGIN(INITIAL); return T_EOL; }
|
|
|
|
.
|
|
|
|
}
|
|
|
|
|
2005-04-17 02:20:36 +04:00
|
|
|
<PARAM>{
|
|
|
|
"&&" return T_AND;
|
|
|
|
"||" return T_OR;
|
|
|
|
"(" return T_OPEN_PAREN;
|
|
|
|
")" return T_CLOSE_PAREN;
|
|
|
|
"!" return T_NOT;
|
|
|
|
"=" return T_EQUAL;
|
|
|
|
"!=" return T_UNEQUAL;
|
2015-06-15 15:00:21 +03:00
|
|
|
"<=" return T_LESS_EQUAL;
|
|
|
|
">=" return T_GREATER_EQUAL;
|
|
|
|
"<" return T_LESS;
|
|
|
|
">" return T_GREATER;
|
2005-04-17 02:20:36 +04:00
|
|
|
\"|\' {
|
|
|
|
str = yytext[0];
|
|
|
|
new_string();
|
|
|
|
BEGIN(STRING);
|
|
|
|
}
|
2018-03-22 20:00:14 +03:00
|
|
|
\n BEGIN(INITIAL); return T_EOL;
|
2015-07-12 10:41:50 +03:00
|
|
|
({n}|[/.])+ {
|
2011-05-05 05:14:44 +04:00
|
|
|
const struct kconf_id *id = kconf_id_lookup(yytext, yyleng);
|
2005-11-09 08:34:52 +03:00
|
|
|
if (id && id->flags & TF_PARAM) {
|
2018-01-11 18:50:50 +03:00
|
|
|
yylval.id = id;
|
2005-11-09 08:34:51 +03:00
|
|
|
return id->token;
|
2005-11-09 08:34:52 +03:00
|
|
|
}
|
2005-04-17 02:20:36 +04:00
|
|
|
alloc_string(yytext, yyleng);
|
2018-01-11 18:50:50 +03:00
|
|
|
yylval.string = text;
|
2005-04-17 02:20:36 +04:00
|
|
|
return T_WORD;
|
|
|
|
}
|
kconfig: reference environment variables directly and remove 'option env='
To get access to environment variables, Kconfig needs to define a
symbol using "option env=" syntax. It is tedious to add a symbol entry
for each environment variable given that we need to define much more
such as 'CC', 'AS', 'srctree' etc. to evaluate the compiler capability
in Kconfig.
Adding '$' for symbol references is grammatically inconsistent.
Looking at the code, the symbols prefixed with 'S' are expanded by:
- conf_expand_value()
This is used to expand 'arch/$ARCH/defconfig' and 'defconfig_list'
- sym_expand_string_value()
This is used to expand strings in 'source' and 'mainmenu'
All of them are fixed values independent of user configuration. So,
they can be changed into the direct expansion instead of symbols.
This change makes the code much cleaner. The bounce symbols 'SRCARCH',
'ARCH', 'SUBARCH', 'KERNELVERSION' are gone.
sym_init() hard-coding 'UNAME_RELEASE' is also gone. 'UNAME_RELEASE'
should be replaced with an environment variable.
ARCH_DEFCONFIG is a normal symbol, so it should be simply referenced
without '$' prefix.
The new syntax is addicted by Make. The variable reference needs
parentheses, like $(FOO), but you can omit them for single-letter
variables, like $F. Yet, in Makefiles, people tend to use the
parenthetical form for consistency / clarification.
At this moment, only the environment variable is supported, but I will
extend the concept of 'variable' later on.
The variables are expanded in the lexer so we can simplify the token
handling on the parser side.
For example, the following code works.
[Example code]
config MY_TOOLCHAIN_LIST
string
default "My tools: CC=$(CC), AS=$(AS), CPP=$(CPP)"
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_MY_TOOLCHAIN_LIST="My tools: CC=gcc, AS=as, CPP=gcc -E"
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
Reviewed-by: Kees Cook <keescook@chromium.org>
2018-05-28 12:21:40 +03:00
|
|
|
({n}|[/.$])+ {
|
|
|
|
/* this token includes at least one '$' */
|
|
|
|
yylval.string = expand_token(yytext, yyleng);
|
|
|
|
if (strlen(yylval.string))
|
|
|
|
return T_WORD;
|
|
|
|
free(yylval.string);
|
|
|
|
}
|
2005-04-17 02:20:36 +04:00
|
|
|
#.* /* comment */
|
2018-03-22 20:00:14 +03:00
|
|
|
\\\n ;
|
2015-01-20 15:52:48 +03:00
|
|
|
[[:blank:]]+
|
2015-07-12 10:41:50 +03:00
|
|
|
. warn_ignored_character(*yytext);
|
2005-04-17 02:20:36 +04:00
|
|
|
<<EOF>> {
|
|
|
|
BEGIN(INITIAL);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
<STRING>{
|
kconfig: reference environment variables directly and remove 'option env='
To get access to environment variables, Kconfig needs to define a
symbol using "option env=" syntax. It is tedious to add a symbol entry
for each environment variable given that we need to define much more
such as 'CC', 'AS', 'srctree' etc. to evaluate the compiler capability
in Kconfig.
Adding '$' for symbol references is grammatically inconsistent.
Looking at the code, the symbols prefixed with 'S' are expanded by:
- conf_expand_value()
This is used to expand 'arch/$ARCH/defconfig' and 'defconfig_list'
- sym_expand_string_value()
This is used to expand strings in 'source' and 'mainmenu'
All of them are fixed values independent of user configuration. So,
they can be changed into the direct expansion instead of symbols.
This change makes the code much cleaner. The bounce symbols 'SRCARCH',
'ARCH', 'SUBARCH', 'KERNELVERSION' are gone.
sym_init() hard-coding 'UNAME_RELEASE' is also gone. 'UNAME_RELEASE'
should be replaced with an environment variable.
ARCH_DEFCONFIG is a normal symbol, so it should be simply referenced
without '$' prefix.
The new syntax is addicted by Make. The variable reference needs
parentheses, like $(FOO), but you can omit them for single-letter
variables, like $F. Yet, in Makefiles, people tend to use the
parenthetical form for consistency / clarification.
At this moment, only the environment variable is supported, but I will
extend the concept of 'variable' later on.
The variables are expanded in the lexer so we can simplify the token
handling on the parser side.
For example, the following code works.
[Example code]
config MY_TOOLCHAIN_LIST
string
default "My tools: CC=$(CC), AS=$(AS), CPP=$(CPP)"
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_MY_TOOLCHAIN_LIST="My tools: CC=gcc, AS=as, CPP=gcc -E"
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
Reviewed-by: Kees Cook <keescook@chromium.org>
2018-05-28 12:21:40 +03:00
|
|
|
"$".* append_expanded_string(yytext);
|
|
|
|
[^$'"\\\n]+/\n {
|
2005-04-17 02:20:36 +04:00
|
|
|
append_string(yytext, yyleng);
|
2018-01-11 18:50:50 +03:00
|
|
|
yylval.string = text;
|
2005-04-17 02:20:36 +04:00
|
|
|
return T_WORD_QUOTE;
|
|
|
|
}
|
kconfig: reference environment variables directly and remove 'option env='
To get access to environment variables, Kconfig needs to define a
symbol using "option env=" syntax. It is tedious to add a symbol entry
for each environment variable given that we need to define much more
such as 'CC', 'AS', 'srctree' etc. to evaluate the compiler capability
in Kconfig.
Adding '$' for symbol references is grammatically inconsistent.
Looking at the code, the symbols prefixed with 'S' are expanded by:
- conf_expand_value()
This is used to expand 'arch/$ARCH/defconfig' and 'defconfig_list'
- sym_expand_string_value()
This is used to expand strings in 'source' and 'mainmenu'
All of them are fixed values independent of user configuration. So,
they can be changed into the direct expansion instead of symbols.
This change makes the code much cleaner. The bounce symbols 'SRCARCH',
'ARCH', 'SUBARCH', 'KERNELVERSION' are gone.
sym_init() hard-coding 'UNAME_RELEASE' is also gone. 'UNAME_RELEASE'
should be replaced with an environment variable.
ARCH_DEFCONFIG is a normal symbol, so it should be simply referenced
without '$' prefix.
The new syntax is addicted by Make. The variable reference needs
parentheses, like $(FOO), but you can omit them for single-letter
variables, like $F. Yet, in Makefiles, people tend to use the
parenthetical form for consistency / clarification.
At this moment, only the environment variable is supported, but I will
extend the concept of 'variable' later on.
The variables are expanded in the lexer so we can simplify the token
handling on the parser side.
For example, the following code works.
[Example code]
config MY_TOOLCHAIN_LIST
string
default "My tools: CC=$(CC), AS=$(AS), CPP=$(CPP)"
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_MY_TOOLCHAIN_LIST="My tools: CC=gcc, AS=as, CPP=gcc -E"
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
Reviewed-by: Kees Cook <keescook@chromium.org>
2018-05-28 12:21:40 +03:00
|
|
|
[^$'"\\\n]+ {
|
2005-04-17 02:20:36 +04:00
|
|
|
append_string(yytext, yyleng);
|
|
|
|
}
|
|
|
|
\\.?/\n {
|
|
|
|
append_string(yytext + 1, yyleng - 1);
|
2018-01-11 18:50:50 +03:00
|
|
|
yylval.string = text;
|
2005-04-17 02:20:36 +04:00
|
|
|
return T_WORD_QUOTE;
|
|
|
|
}
|
|
|
|
\\.? {
|
|
|
|
append_string(yytext + 1, yyleng - 1);
|
|
|
|
}
|
|
|
|
\'|\" {
|
|
|
|
if (str == yytext[0]) {
|
|
|
|
BEGIN(PARAM);
|
2018-01-11 18:50:50 +03:00
|
|
|
yylval.string = text;
|
2005-04-17 02:20:36 +04:00
|
|
|
return T_WORD_QUOTE;
|
|
|
|
} else
|
|
|
|
append_string(yytext, 1);
|
|
|
|
}
|
|
|
|
\n {
|
2018-02-06 03:34:41 +03:00
|
|
|
fprintf(stderr,
|
|
|
|
"%s:%d:warning: multi-line strings not supported\n",
|
|
|
|
zconf_curname(), zconf_lineno());
|
2005-04-17 02:20:36 +04:00
|
|
|
BEGIN(INITIAL);
|
|
|
|
return T_EOL;
|
|
|
|
}
|
|
|
|
<<EOF>> {
|
|
|
|
BEGIN(INITIAL);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
<HELP>{
|
|
|
|
[ \t]+ {
|
|
|
|
ts = 0;
|
|
|
|
for (i = 0; i < yyleng; i++) {
|
|
|
|
if (yytext[i] == '\t')
|
|
|
|
ts = (ts & ~7) + 8;
|
|
|
|
else
|
|
|
|
ts++;
|
|
|
|
}
|
|
|
|
last_ts = ts;
|
|
|
|
if (first_ts) {
|
|
|
|
if (ts < first_ts) {
|
|
|
|
zconf_endhelp();
|
|
|
|
return T_HELPTEXT;
|
|
|
|
}
|
|
|
|
ts -= first_ts;
|
|
|
|
while (ts > 8) {
|
|
|
|
append_string(" ", 8);
|
|
|
|
ts -= 8;
|
|
|
|
}
|
|
|
|
append_string(" ", ts);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
[ \t]*\n/[^ \t\n] {
|
|
|
|
zconf_endhelp();
|
|
|
|
return T_HELPTEXT;
|
|
|
|
}
|
|
|
|
[ \t]*\n {
|
|
|
|
append_string("\n", 1);
|
|
|
|
}
|
|
|
|
[^ \t\n].* {
|
2008-01-12 01:55:20 +03:00
|
|
|
while (yyleng) {
|
|
|
|
if ((yytext[yyleng-1] != ' ') && (yytext[yyleng-1] != '\t'))
|
|
|
|
break;
|
|
|
|
yyleng--;
|
|
|
|
}
|
2005-04-17 02:20:36 +04:00
|
|
|
append_string(yytext, yyleng);
|
|
|
|
if (!first_ts)
|
|
|
|
first_ts = last_ts;
|
|
|
|
}
|
|
|
|
<<EOF>> {
|
|
|
|
zconf_endhelp();
|
|
|
|
return T_HELPTEXT;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
<<EOF>> {
|
2005-11-09 08:34:53 +03:00
|
|
|
if (current_file) {
|
2005-04-17 02:20:36 +04:00
|
|
|
zconf_endfile();
|
2005-11-09 08:34:53 +03:00
|
|
|
return T_EOL;
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|
|
|
|
fclose(yyin);
|
|
|
|
yyterminate();
|
|
|
|
}
|
|
|
|
|
|
|
|
%%
|
kconfig: reference environment variables directly and remove 'option env='
To get access to environment variables, Kconfig needs to define a
symbol using "option env=" syntax. It is tedious to add a symbol entry
for each environment variable given that we need to define much more
such as 'CC', 'AS', 'srctree' etc. to evaluate the compiler capability
in Kconfig.
Adding '$' for symbol references is grammatically inconsistent.
Looking at the code, the symbols prefixed with 'S' are expanded by:
- conf_expand_value()
This is used to expand 'arch/$ARCH/defconfig' and 'defconfig_list'
- sym_expand_string_value()
This is used to expand strings in 'source' and 'mainmenu'
All of them are fixed values independent of user configuration. So,
they can be changed into the direct expansion instead of symbols.
This change makes the code much cleaner. The bounce symbols 'SRCARCH',
'ARCH', 'SUBARCH', 'KERNELVERSION' are gone.
sym_init() hard-coding 'UNAME_RELEASE' is also gone. 'UNAME_RELEASE'
should be replaced with an environment variable.
ARCH_DEFCONFIG is a normal symbol, so it should be simply referenced
without '$' prefix.
The new syntax is addicted by Make. The variable reference needs
parentheses, like $(FOO), but you can omit them for single-letter
variables, like $F. Yet, in Makefiles, people tend to use the
parenthetical form for consistency / clarification.
At this moment, only the environment variable is supported, but I will
extend the concept of 'variable' later on.
The variables are expanded in the lexer so we can simplify the token
handling on the parser side.
For example, the following code works.
[Example code]
config MY_TOOLCHAIN_LIST
string
default "My tools: CC=$(CC), AS=$(AS), CPP=$(CPP)"
[Result]
$ make -s alldefconfig && tail -n 1 .config
CONFIG_MY_TOOLCHAIN_LIST="My tools: CC=gcc, AS=as, CPP=gcc -E"
Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
Reviewed-by: Kees Cook <keescook@chromium.org>
2018-05-28 12:21:40 +03:00
|
|
|
static char *expand_token(const char *in, size_t n)
|
|
|
|
{
|
|
|
|
char *out;
|
|
|
|
int c;
|
|
|
|
char c2;
|
|
|
|
const char *rest, *end;
|
|
|
|
|
|
|
|
new_string();
|
|
|
|
append_string(in, n);
|
|
|
|
|
|
|
|
/* get the whole line because we do not know the end of token. */
|
|
|
|
while ((c = input()) != EOF) {
|
|
|
|
if (c == '\n') {
|
|
|
|
unput(c);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
c2 = c;
|
|
|
|
append_string(&c2, 1);
|
|
|
|
}
|
|
|
|
|
|
|
|
rest = text;
|
|
|
|
out = expand_one_token(&rest);
|
|
|
|
|
|
|
|
/* push back unused characters to the input stream */
|
|
|
|
end = rest + strlen(rest);
|
|
|
|
while (end > rest)
|
|
|
|
unput(*--end);
|
|
|
|
|
|
|
|
free(text);
|
|
|
|
|
|
|
|
return out;
|
|
|
|
}
|
|
|
|
|
|
|
|
static void append_expanded_string(const char *str)
|
|
|
|
{
|
|
|
|
const char *end;
|
|
|
|
char *res;
|
|
|
|
|
|
|
|
str++;
|
|
|
|
|
|
|
|
res = expand_dollar(&str);
|
|
|
|
|
|
|
|
/* push back unused characters to the input stream */
|
|
|
|
end = str + strlen(str);
|
|
|
|
while (end > str)
|
|
|
|
unput(*--end);
|
|
|
|
|
|
|
|
append_string(res, strlen(res));
|
|
|
|
|
|
|
|
free(res);
|
|
|
|
}
|
|
|
|
|
2005-04-17 02:20:36 +04:00
|
|
|
void zconf_starthelp(void)
|
|
|
|
{
|
|
|
|
new_string();
|
|
|
|
last_ts = first_ts = 0;
|
|
|
|
BEGIN(HELP);
|
|
|
|
}
|
|
|
|
|
|
|
|
static void zconf_endhelp(void)
|
|
|
|
{
|
2018-01-11 18:50:50 +03:00
|
|
|
yylval.string = text;
|
2005-04-17 02:20:36 +04:00
|
|
|
BEGIN(INITIAL);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Try to open specified file with following names:
|
|
|
|
* ./name
|
|
|
|
* $(srctree)/name
|
|
|
|
* The latter is used when srctree is separate from objtree
|
|
|
|
* when compiling the kernel.
|
|
|
|
* Return NULL if file is not found.
|
|
|
|
*/
|
|
|
|
FILE *zconf_fopen(const char *name)
|
|
|
|
{
|
|
|
|
char *env, fullname[PATH_MAX+1];
|
|
|
|
FILE *f;
|
|
|
|
|
|
|
|
f = fopen(name, "r");
|
2007-05-06 00:49:00 +04:00
|
|
|
if (!f && name != NULL && name[0] != '/') {
|
2005-04-17 02:20:36 +04:00
|
|
|
env = getenv(SRCTREE);
|
|
|
|
if (env) {
|
|
|
|
sprintf(fullname, "%s/%s", env, name);
|
|
|
|
f = fopen(fullname, "r");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return f;
|
|
|
|
}
|
|
|
|
|
|
|
|
void zconf_initscan(const char *name)
|
|
|
|
{
|
|
|
|
yyin = zconf_fopen(name);
|
|
|
|
if (!yyin) {
|
2018-02-06 03:34:41 +03:00
|
|
|
fprintf(stderr, "can't find file %s\n", name);
|
2005-04-17 02:20:36 +04:00
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
|
2012-11-06 18:32:08 +04:00
|
|
|
current_buf = xmalloc(sizeof(*current_buf));
|
2005-04-17 02:20:36 +04:00
|
|
|
memset(current_buf, 0, sizeof(*current_buf));
|
|
|
|
|
|
|
|
current_file = file_lookup(name);
|
2018-03-22 20:00:14 +03:00
|
|
|
yylineno = 1;
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|
|
|
|
|
|
|
|
void zconf_nextfile(const char *name)
|
|
|
|
{
|
2011-02-24 21:36:42 +03:00
|
|
|
struct file *iter;
|
2005-04-17 02:20:36 +04:00
|
|
|
struct file *file = file_lookup(name);
|
2012-11-06 18:32:08 +04:00
|
|
|
struct buffer *buf = xmalloc(sizeof(*buf));
|
2005-04-17 02:20:36 +04:00
|
|
|
memset(buf, 0, sizeof(*buf));
|
|
|
|
|
|
|
|
current_buf->state = YY_CURRENT_BUFFER;
|
2010-09-05 00:09:26 +04:00
|
|
|
yyin = zconf_fopen(file->name);
|
2005-04-17 02:20:36 +04:00
|
|
|
if (!yyin) {
|
2018-02-06 03:34:41 +03:00
|
|
|
fprintf(stderr, "%s:%d: can't open file \"%s\"\n",
|
|
|
|
zconf_curname(), zconf_lineno(), file->name);
|
2005-04-17 02:20:36 +04:00
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
yy_switch_to_buffer(yy_create_buffer(yyin, YY_BUF_SIZE));
|
|
|
|
buf->parent = current_buf;
|
|
|
|
current_buf = buf;
|
|
|
|
|
2018-03-22 20:00:14 +03:00
|
|
|
current_file->lineno = yylineno;
|
2018-03-22 20:00:13 +03:00
|
|
|
file->parent = current_file;
|
|
|
|
|
|
|
|
for (iter = current_file; iter; iter = iter->parent) {
|
|
|
|
if (!strcmp(iter->name, file->name)) {
|
2018-02-06 03:34:41 +03:00
|
|
|
fprintf(stderr,
|
2018-03-22 20:00:12 +03:00
|
|
|
"Recursive inclusion detected.\n"
|
|
|
|
"Inclusion path:\n"
|
2018-03-22 20:00:13 +03:00
|
|
|
" current file : %s\n", file->name);
|
|
|
|
iter = file;
|
2018-03-02 10:05:12 +03:00
|
|
|
do {
|
2011-02-24 21:36:42 +03:00
|
|
|
iter = iter->parent;
|
2018-03-22 20:00:12 +03:00
|
|
|
fprintf(stderr, " included from: %s:%d\n",
|
2018-03-02 10:05:12 +03:00
|
|
|
iter->name, iter->lineno - 1);
|
2018-03-22 20:00:13 +03:00
|
|
|
} while (strcmp(iter->name, file->name));
|
2011-02-24 21:36:42 +03:00
|
|
|
exit(1);
|
|
|
|
}
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|
2018-03-22 20:00:13 +03:00
|
|
|
|
2018-03-22 20:00:14 +03:00
|
|
|
yylineno = 1;
|
2005-04-17 02:20:36 +04:00
|
|
|
current_file = file;
|
|
|
|
}
|
|
|
|
|
2005-11-09 08:34:53 +03:00
|
|
|
static void zconf_endfile(void)
|
2005-04-17 02:20:36 +04:00
|
|
|
{
|
|
|
|
struct buffer *parent;
|
|
|
|
|
|
|
|
current_file = current_file->parent;
|
2018-03-22 20:00:14 +03:00
|
|
|
if (current_file)
|
|
|
|
yylineno = current_file->lineno;
|
2005-04-17 02:20:36 +04:00
|
|
|
|
|
|
|
parent = current_buf->parent;
|
|
|
|
if (parent) {
|
|
|
|
fclose(yyin);
|
|
|
|
yy_delete_buffer(YY_CURRENT_BUFFER);
|
|
|
|
yy_switch_to_buffer(parent->state);
|
|
|
|
}
|
|
|
|
free(current_buf);
|
|
|
|
current_buf = parent;
|
|
|
|
}
|
|
|
|
|
|
|
|
int zconf_lineno(void)
|
|
|
|
{
|
2005-11-09 08:34:53 +03:00
|
|
|
return current_pos.lineno;
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|
|
|
|
|
2010-09-05 00:03:30 +04:00
|
|
|
const char *zconf_curname(void)
|
2005-04-17 02:20:36 +04:00
|
|
|
{
|
2005-11-09 08:34:53 +03:00
|
|
|
return current_pos.file ? current_pos.file->name : "<none>";
|
2005-04-17 02:20:36 +04:00
|
|
|
}
|