mirror of
https://github.com/torvalds/linux.git
synced 2026-04-18 06:44:00 -04:00
kconfig: Error out on duplicated kconfig inclusion
Let kconfig exit with error on duplicated Kconfig file inclusion.
Repeated inclusion of Kbuild files are considered bad-practise with
regard to maintenance; and Kconfig language is rich enough that there
should be no need for that.
If repeated inclusion of Kconfig files is detected, error out with
messages like:
Kconfig.inc1:4: error: repeated inclusion of Kconfig.inc3
Kconfig.inc2:3: note: location of first inclusion of Kconfig.inc3
While commit f094f8a1b2 ("kconfig: allow multiple inclusion of the
same file") introduced detection of recursive inclusions of Kconfig
files, it explicitly allowed repeated inclusions, unfortunately w/o
reasoning.
Reported-by: Linus Torvalds <torvalds@linux-foundation.org>
Closes: https://lore.kernel.org/all/CAHk-=wj03hLzK2D=+OYmjgcmGM+XYymp8GyaEs=C0=rXG2nb7w@mail.gmail.com/
Reviewed-by: Nathan Chancellor <nathan@kernel.org>
Tested-by: Nathan Chancellor <nathan@kernel.org>
Link: https://patch.msgid.link/20260220-kconfig-error-out-on-duplicated-inclusion-v1-1-be78aa241a53@kernel.org
Signed-off-by: Nicolas Schier <nsc@kernel.org>
This commit is contained in:
@@ -402,7 +402,7 @@ void zconf_initscan(const char *name)
|
||||
exit(1);
|
||||
}
|
||||
|
||||
cur_filename = file_lookup(name);
|
||||
cur_filename = file_lookup(name, NULL, 0);
|
||||
yylineno = 1;
|
||||
}
|
||||
|
||||
@@ -443,7 +443,7 @@ void zconf_nextfile(const char *name)
|
||||
}
|
||||
|
||||
yylineno = 1;
|
||||
cur_filename = file_lookup(name);
|
||||
cur_filename = file_lookup(name, cur_filename, cur_lineno);
|
||||
}
|
||||
|
||||
static void zconf_endfile(void)
|
||||
|
||||
@@ -51,7 +51,8 @@ static inline void xfwrite(const void *str, size_t len, size_t count, FILE *out)
|
||||
}
|
||||
|
||||
/* util.c */
|
||||
const char *file_lookup(const char *name);
|
||||
const char *file_lookup(const char *name,
|
||||
const char *parent_name, int parent_lineno);
|
||||
|
||||
/* lexer.l */
|
||||
int yylex(void);
|
||||
|
||||
3
scripts/kconfig/tests/err_repeated_inc/Kconfig
Normal file
3
scripts/kconfig/tests/err_repeated_inc/Kconfig
Normal file
@@ -0,0 +1,3 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-only
|
||||
|
||||
source "Kconfig.inc1"
|
||||
4
scripts/kconfig/tests/err_repeated_inc/Kconfig.inc1
Normal file
4
scripts/kconfig/tests/err_repeated_inc/Kconfig.inc1
Normal file
@@ -0,0 +1,4 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-only
|
||||
|
||||
source "Kconfig.inc2"
|
||||
source "Kconfig.inc3"
|
||||
3
scripts/kconfig/tests/err_repeated_inc/Kconfig.inc2
Normal file
3
scripts/kconfig/tests/err_repeated_inc/Kconfig.inc2
Normal file
@@ -0,0 +1,3 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-only
|
||||
|
||||
source "Kconfig.inc3"
|
||||
1
scripts/kconfig/tests/err_repeated_inc/Kconfig.inc3
Normal file
1
scripts/kconfig/tests/err_repeated_inc/Kconfig.inc3
Normal file
@@ -0,0 +1 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-only
|
||||
10
scripts/kconfig/tests/err_repeated_inc/__init__.py
Normal file
10
scripts/kconfig/tests/err_repeated_inc/__init__.py
Normal file
@@ -0,0 +1,10 @@
|
||||
# SPDX-License-Identifier: GPL-2.0
|
||||
"""
|
||||
Detect repeated inclusion error.
|
||||
|
||||
If repeated inclusion is detected, it should fail with error message.
|
||||
"""
|
||||
|
||||
def test(conf):
|
||||
assert conf.oldaskconfig() != 0
|
||||
assert conf.stderr_contains('expected_stderr')
|
||||
2
scripts/kconfig/tests/err_repeated_inc/expected_stderr
Normal file
2
scripts/kconfig/tests/err_repeated_inc/expected_stderr
Normal file
@@ -0,0 +1,2 @@
|
||||
Kconfig.inc1:4: error: Repeated inclusion of Kconfig.inc3
|
||||
Kconfig.inc2:3: note: Location of first inclusion of Kconfig.inc3
|
||||
@@ -18,25 +18,50 @@ static HASHTABLE_DEFINE(file_hashtable, 1U << 11);
|
||||
|
||||
struct file {
|
||||
struct hlist_node node;
|
||||
struct {
|
||||
const char *name;
|
||||
int lineno;
|
||||
} parent;
|
||||
char name[];
|
||||
};
|
||||
|
||||
/* file already present in list? If not add it */
|
||||
const char *file_lookup(const char *name)
|
||||
static void die_duplicated_include(struct file *file,
|
||||
const char *parent, int lineno)
|
||||
{
|
||||
fprintf(stderr,
|
||||
"%s:%d: error: repeated inclusion of %s\n"
|
||||
"%s:%d: note: location of first inclusion of %s\n",
|
||||
parent, lineno, file->name,
|
||||
file->parent.name, file->parent.lineno, file->name);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
/* file already present in list? If not add it */
|
||||
const char *file_lookup(const char *name,
|
||||
const char *parent_name, int parent_lineno)
|
||||
{
|
||||
const char *parent = NULL;
|
||||
struct file *file;
|
||||
size_t len;
|
||||
int hash = hash_str(name);
|
||||
|
||||
if (parent_name)
|
||||
parent = file_lookup(parent_name, NULL, 0);
|
||||
|
||||
hash_for_each_possible(file_hashtable, file, node, hash)
|
||||
if (!strcmp(name, file->name))
|
||||
return file->name;
|
||||
if (!strcmp(name, file->name)) {
|
||||
if (!parent_name)
|
||||
return file->name;
|
||||
die_duplicated_include(file, parent, parent_lineno);
|
||||
}
|
||||
|
||||
len = strlen(name);
|
||||
file = xmalloc(sizeof(*file) + len + 1);
|
||||
memset(file, 0, sizeof(*file));
|
||||
memcpy(file->name, name, len);
|
||||
file->name[len] = '\0';
|
||||
file->parent.name = parent;
|
||||
file->parent.lineno = parent_lineno;
|
||||
|
||||
hash_add(file_hashtable, &file->node, hash);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user