From 3e555d59dd651366e14d6d6a47668acec3039fff Mon Sep 17 00:00:00 2001 From: Dirk Gouders Date: Wed, 30 Oct 2013 10:44:54 +0100 Subject: [PATCH] kconfig/symbol.c: handle choice_values that depend on 'm' symbols If choices consist of choice_values that depend on symbols set to 'm', those choice_values are not set to 'n' if the choice is changed from 'm' to 'y' (in which case only one active choice_value is allowed). Those values are also written to the config file causing modules when they should not. The following config can be used to reproduce and examine the problem: config modules boolean modules default y option modules config dependency tristate "Dependency" default m choice prompt "Tristate Choice" default choice0 config choice0 tristate "Choice 0" config choice1 tristate "Choice 1" depends on dependency endchoice This patch handles choice_values that depend on symbols set to 'm' if the corresponding choice is set to 'y'. Reported-by: Sebastian Andrzej Siewior Signed-off-by: Dirk Gouders --- scripts/kconfig/symbol.c | 26 ++++++++++++++++++++++---- 1 file changed, 22 insertions(+), 4 deletions(-) diff --git a/scripts/kconfig/symbol.c b/scripts/kconfig/symbol.c index c9a6775..043c041 100644 --- a/scripts/kconfig/symbol.c +++ b/scripts/kconfig/symbol.c @@ -338,10 +338,27 @@ void sym_calc_value(struct symbol *sym) switch (sym_get_type(sym)) { case S_BOOLEAN: - case S_TRISTATE: - if (sym_is_choice_value(sym) && sym->visible == yes) { - prop = sym_get_choice_prop(sym); - newval.tri = (prop_get_symbol(prop)->curr.val == sym) ? yes : no; + case S_TRISTATE: { + struct symbol *choice_sym = NULL; + + if (sym_is_choice_value(sym)) + choice_sym = prop_get_symbol(sym_get_choice_prop(sym)); + + /* + * If this is a visible choice_value we want to check + * if it is the currently selected, in two cases: + * + * 1) If it's visibility is 'yes'. + * 2) If it's visibility is 'mod' and the correspondig + * choice symbols' value is 'yes'. + * + * If a choice symbol is 'yes', only the selected + * choice_value may be 'yes' and all others (also + * those currently set to 'mod') must be set to 'no'. + */ + if (choice_sym && + (sym->visible == yes || (sym->visible == mod && choice_sym->curr.tri == yes))) { + newval.tri = choice_sym->curr.val == sym ? yes : no; } else { if (sym->visible != no) { /* if the symbol is visible use the user value @@ -382,6 +399,7 @@ void sym_calc_value(struct symbol *sym) if (newval.tri == mod && sym_get_type(sym) == S_BOOLEAN) newval.tri = yes; break; + } case S_STRING: case S_HEX: case S_INT: -- 1.8.3.2