From 9c194a0ba78c1504ac969ef0522d63d9f2a0c550 Mon Sep 17 00:00:00 2001 From: Jaroslav Kysela Date: Fri, 5 Mar 2021 18:50:02 +0100 Subject: [PATCH] ucm: add _fboot / FixedBootSequence Actually, the BootSequence is executed only when the driver controls (identifiers or value types) are changed. It may be handy to have also a sequence which is executed at _each_ boot without any condition. Signed-off-by: Jaroslav Kysela --- include/use-case.h | 3 +++ src/ucm/main.c | 25 ++++++++++++++++++++++++- src/ucm/parser.c | 28 ++++++++++++++++++++++++++++ src/ucm/ucm_local.h | 3 +++ src/ucm/utils.c | 1 + 5 files changed, 59 insertions(+), 1 deletion(-) diff --git a/include/use-case.h b/include/use-case.h index 2363c3ed..13e5e3a3 100644 --- a/include/use-case.h +++ b/include/use-case.h @@ -418,7 +418,10 @@ int snd_use_case_geti(snd_use_case_mgr_t *uc_mgr, * \return Zero if success, otherwise a negative error code * * Known identifiers: + * - _fboot - execute the fixed boot sequence (value = NULL) * - _boot - execute the boot sequence (value = NULL) + * - only when driver controls identifiers are changed + * (otherwise the old control values are restored) * - _defaults - execute the 'defaults' sequence (value = NULL) * - _verb - set current verb = value * - _enadev - enable given device = value diff --git a/src/ucm/main.c b/src/ucm/main.c index 754b967e..8ac99de0 100644 --- a/src/ucm/main.c +++ b/src/ucm/main.c @@ -594,6 +594,8 @@ static int check_empty_configuration(snd_use_case_mgr_t *uc_mgr) } if (!list_empty(&uc_mgr->verb_list)) return 0; + if (!list_empty(&uc_mgr->fixedboot_list)) + return 0; if (!list_empty(&uc_mgr->boot_list)) return 0; return -ENXIO; @@ -993,6 +995,7 @@ int snd_use_case_mgr_open(snd_use_case_mgr_t **uc_mgr, if (mgr == NULL) return -ENOMEM; INIT_LIST_HEAD(&mgr->verb_list); + INIT_LIST_HEAD(&mgr->fixedboot_list); INIT_LIST_HEAD(&mgr->boot_list); INIT_LIST_HEAD(&mgr->default_list); INIT_LIST_HEAD(&mgr->value_list); @@ -1886,6 +1889,24 @@ int snd_use_case_geti(snd_use_case_mgr_t *uc_mgr, return err; } +static int set_fixedboot_user(snd_use_case_mgr_t *uc_mgr, + const char *value) +{ + int err; + + if (value != NULL && *value) { + uc_error("error: wrong value for _fboot (%s)", value); + return -EINVAL; + } + err = execute_sequence(uc_mgr, &uc_mgr->fixedboot_list, + &uc_mgr->value_list, NULL, NULL); + if (err < 0) { + uc_error("Unable to execute force boot sequence"); + return err; + } + return err; +} + static int set_boot_user(snd_use_case_mgr_t *uc_mgr, const char *value) { @@ -2125,7 +2146,9 @@ int snd_use_case_set(snd_use_case_mgr_t *uc_mgr, int err = 0; pthread_mutex_lock(&uc_mgr->mutex); - if (strcmp(identifier, "_boot") == 0) + if (strcmp(identifier, "_fboot") == 0) + err = set_fixedboot_user(uc_mgr, value); + else if (strcmp(identifier, "_boot") == 0) err = set_boot_user(uc_mgr, value); else if (strcmp(identifier, "_defaults") == 0) err = set_defaults_user(uc_mgr, value); diff --git a/src/ucm/parser.c b/src/ucm/parser.c index a5be791d..55781f87 100644 --- a/src/ucm/parser.c +++ b/src/ucm/parser.c @@ -1739,6 +1739,26 @@ __error: return err; } +/* + * parse controls which should be run only at initial boot (forcefully) + */ +static int parse_controls_fixedboot(snd_use_case_mgr_t *uc_mgr, snd_config_t *cfg) +{ + int err; + + if (!list_empty(&uc_mgr->fixedboot_list)) { + uc_error("FixedBoot list is not empty"); + return -EINVAL; + } + err = parse_sequence(uc_mgr, &uc_mgr->fixedboot_list, cfg); + if (err < 0) { + uc_error("Unable to parse FixedBootSequence"); + return err; + } + + return 0; +} + /* * parse controls which should be run only at initial boot */ @@ -1891,6 +1911,14 @@ static int parse_master_file(snd_use_case_mgr_t *uc_mgr, snd_config_t *cfg) continue; } + /* find default control values section (force boot sequence only) */ + if (strcmp(id, "FixedBootSequence") == 0) { + err = parse_controls_fixedboot(uc_mgr, n); + if (err < 0) + return err; + continue; + } + /* find default control values section (first boot only) */ if (strcmp(id, "BootSequence") == 0) { err = parse_controls_boot(uc_mgr, n); diff --git a/src/ucm/ucm_local.h b/src/ucm/ucm_local.h index f99cd5db..c3e5a079 100644 --- a/src/ucm/ucm_local.h +++ b/src/ucm/ucm_local.h @@ -222,6 +222,9 @@ struct snd_use_case_mgr { /* use case verb, devices and modifier configs parsed from files */ struct list_head verb_list; + /* force boot settings - sequence */ + struct list_head fixedboot_list; + /* boot settings - sequence */ struct list_head boot_list; diff --git a/src/ucm/utils.c b/src/ucm/utils.c index f1fd8e92..24d06310 100644 --- a/src/ucm/utils.c +++ b/src/ucm/utils.c @@ -692,6 +692,7 @@ void uc_mgr_free_verb(snd_use_case_mgr_t *uc_mgr) list_del(&verb->list); free(verb); } + uc_mgr_free_sequence(&uc_mgr->fixedboot_list); uc_mgr_free_sequence(&uc_mgr->boot_list); uc_mgr_free_sequence(&uc_mgr->default_list); uc_mgr_free_value(&uc_mgr->value_list); -- 2.47.1