kconfig: introduce choice_set_value() helper

Currently, sym_set_tristate_value() is used to set 'y' to a choice
member, which is confusing because it not only sets 'y' to the given
symbol but also tweaks flags of other symbols as a side effect.

Add a dedicated function for setting the value of the given choice.

Signed-off-by: Masahiro Yamada <masahiroy@kernel.org>
This commit is contained in:
Masahiro Yamada 2024-06-12 02:55:12 +09:00
parent dfe8e56fc6
commit bd988e7cb8
5 changed files with 47 additions and 22 deletions

View File

@ -507,7 +507,7 @@ static void conf_choice(struct menu *menu)
print_help(child);
continue;
}
sym_set_tristate_value(child->sym, yes);
choice_set_value(menu, child->sym);
return;
}
}

View File

@ -28,6 +28,7 @@ bool sym_dep_errors(void);
enum symbol_type sym_get_type(struct symbol *sym);
bool sym_tristate_within_range(struct symbol *sym,tristate tri);
bool sym_set_tristate_value(struct symbol *sym,tristate tri);
void choice_set_value(struct menu *choice, struct symbol *sym);
tristate sym_toggle_tristate_value(struct symbol *sym);
bool sym_string_valid(struct symbol *sym, const char *newval);
bool sym_string_within_range(struct symbol *sym, const char *str);

View File

@ -636,7 +636,7 @@ static void conf_choice(struct menu *menu)
if (!child->sym)
break;
sym_set_tristate_value(child->sym, yes);
choice_set_value(menu, child->sym);
}
return;
case 1:

View File

@ -1331,7 +1331,7 @@ static void conf_choice(struct menu *menu)
case ' ':
case 10:
case KEY_RIGHT:
sym_set_tristate_value(child->sym, yes);
choice_set_value(menu, child->sym);
return;
case 'h':
case '?':

View File

@ -516,8 +516,6 @@ bool sym_tristate_within_range(struct symbol *sym, tristate val)
return false;
if (sym->visible <= sym->rev_dep.tri)
return false;
if (sym_is_choice_value(sym) && sym->visible == yes)
return val == yes;
return val >= sym->rev_dep.tri && val <= sym->visible;
}
@ -532,23 +530,6 @@ bool sym_set_tristate_value(struct symbol *sym, tristate val)
sym->flags |= SYMBOL_DEF_USER;
sym_set_changed(sym);
}
/*
* setting a choice value also resets the new flag of the choice
* symbol and all other choice values.
*/
if (sym_is_choice_value(sym) && val == yes) {
struct symbol *cs = prop_get_symbol(sym_get_choice_prop(sym));
struct property *prop;
struct expr *e;
cs->def[S_DEF_USER].val = sym;
cs->flags |= SYMBOL_DEF_USER;
prop = sym_get_choice_prop(cs);
for (e = prop->expr; e; e = e->left.expr) {
if (e->right.sym->visible != no)
e->right.sym->flags |= SYMBOL_DEF_USER;
}
}
sym->def[S_DEF_USER].tri = val;
if (oldval != val)
@ -557,10 +538,53 @@ bool sym_set_tristate_value(struct symbol *sym, tristate val)
return true;
}
/**
* choice_set_value - set the user input to a choice
*
* @choice: menu entry for the choice
* @sym: selected symbol
*/
void choice_set_value(struct menu *choice, struct symbol *sym)
{
struct menu *menu;
bool changed = false;
menu_for_each_sub_entry(menu, choice) {
tristate val;
if (!menu->sym)
continue;
if (menu->sym->visible == no)
continue;
val = menu->sym == sym ? yes : no;
if (menu->sym->curr.tri != val)
changed = true;
menu->sym->def[S_DEF_USER].tri = val;
menu->sym->flags |= SYMBOL_DEF_USER;
}
choice->sym->def[S_DEF_USER].val = sym;
choice->sym->flags |= SYMBOL_DEF_USER;
if (changed)
sym_clear_all_valid();
}
tristate sym_toggle_tristate_value(struct symbol *sym)
{
struct menu *choice;
tristate oldval, newval;
choice = sym_get_choice_menu(sym);
if (choice) {
choice_set_value(choice, sym);
return yes;
}
oldval = newval = sym_get_tristate_value(sym);
do {
switch (newval) {