]> git.alsa-project.org Git - alsa-utils.git/commitdiff
alsactl: ucm: restore controls for other cards in group
authorJaroslav Kysela <perex@perex.cz>
Thu, 4 Dec 2025 14:06:39 +0000 (15:06 +0100)
committerJaroslav Kysela <perex@perex.cz>
Thu, 4 Dec 2025 14:08:14 +0000 (15:08 +0100)
When the primary card restores controls, all other cards
in the card group should do this operation, too.

Signed-off-by: Jaroslav Kysela <perex@perex.cz>
alsactl/alsactl.h
alsactl/boot_params.c
alsactl/state.c

index 994485a47c3a237a611279152531747552d9b94a..2aefb899c30b0add76623d22edc392a73bf21142 100644 (file)
@@ -98,6 +98,7 @@ int state_daemon(const char *file, const char *cardname, int period,
 int state_daemon_kill(const char *pidfile, const char *cmd);
 int clean(const char *cardname, char *const *extra_args);
 int snd_card_clean_cfgdir(const char *cfgdir, int cardno);
+void add_linked_card(int cardno);
 
 /* export */
 
index 736597e7c8ef975331c3552cd5b1e206600111bf..f44526aa78d6aafb06b80f6413a02faffae064bf 100644 (file)
@@ -893,6 +893,8 @@ static void boot_params_update_restored(snd_config_t *card_compound, int skip_ca
                        goto _next;
                }
 
+               add_linked_card(card_val);
+
 _next:
                snd_ctl_close(handle);
        }
index c6a16300d43216234036feaea2b2abd8897e0101..2942f3ffd7414d9bae5e60d81f86293fd760e31f 100644 (file)
 #include <errno.h>
 #include "alsactl.h"
 
+static int linked_cards[16];
+
+static void init_linked_cards(void)
+{
+       size_t index;
+
+       for (index = 0; index < ARRAY_SIZE(linked_cards); index++)
+               linked_cards[index] = -1;
+}
+
+void add_linked_card(int cardno)
+{
+       size_t index;
+
+       for (index = 0; index < ARRAY_SIZE(linked_cards); index++) {
+               if (linked_cards[index] == cardno)
+                       return;
+       }
+
+       for (index = 0; index < ARRAY_SIZE(linked_cards); index++) {
+               if (linked_cards[index] < 0) {
+                       linked_cards[index] = cardno;
+                       return;
+               }
+       }
+       error("Too many linked cards!");
+}
 
 static char *id_str(snd_ctl_elem_id_t *id)
 {
@@ -1703,10 +1730,11 @@ int load_state(const char *cfgdir, const char *file,
               const char *initfile, int initflags,
               const char *cardname, int do_init)
 {
-       int err, finalerr = 0, open_failed, lock_fd;
+       int err, finalerr = 0, open_failed, lock_fd, cardno;
        struct snd_card_iterator iter;
        snd_config_t *config;
        const char *cardname1;
+       size_t index;
 
        config = NULL;
        err = load_configuration(file, &config, &open_failed);
@@ -1723,6 +1751,7 @@ int load_state(const char *cfgdir, const char *file,
                while ((cardname1 = snd_card_iterator_next(&iter)) != NULL) {
                        if (!do_init)
                                break;
+                       init_linked_cards();
                        if (initflags & FLAG_UCM_WAIT)
                                wait_for_card(-1, iter.card);
                        lock_fd = card_lock(iter.card, LOCK_TIMEOUT);
@@ -1752,6 +1781,7 @@ int load_state(const char *cfgdir, const char *file,
        if (err < 0)
                goto out;
        while ((cardname1 = snd_card_iterator_next(&iter)) != NULL) {
+               init_linked_cards();
                if (initflags & FLAG_UCM_WAIT)
                        wait_for_card(-1, iter.card);
                lock_fd = card_lock(iter.card, LOCK_TIMEOUT);
@@ -1780,6 +1810,17 @@ int load_state(const char *cfgdir, const char *file,
                                finalerr = err;
                        initfailed(iter.card, "restore", err);
                }
+               /* for linked cards, restore controls, too */
+               for (index = 0; index < ARRAY_SIZE(linked_cards); index++) {
+                       if ((cardno = linked_cards[index]) < 0)
+                               break;
+                       dbg("Restore for linked card %d", cardno);
+                       if ((err = set_controls(cardno, config, 1))) {
+                               if (!force_restore)
+                                       finalerr = err;
+                               initfailed(cardno, "restore", err);
+                       }
+               }
 unlock_card:
                card_unlock(lock_fd, iter.card);
        }