OSDN Git Service

conf: Allow for a directory to be given as a config file.
authorColin Guthrie <colin@mageia.org>
Fri, 16 Sep 2011 09:04:26 +0000 (10:04 +0100)
committerTakashi Iwai <tiwai@suse.de>
Tue, 20 Sep 2011 07:28:46 +0000 (09:28 +0200)
When this is done, *.conf files can be placed in that directory and they
will be processed by as if they were included directly.

A directory (typically /usr/share/alsa/alsa.conf.d/) has been
added into the distribution.

v2: Used existing conf syntax rather than processing via autotools
v3: Split file loading into separate function and made error handling
more consistent.

Signed-off-by: Colin Guthrie <colin@mageia.org>
Signed-off-by: Takashi Iwai <tiwai@suse.de>
configure.in
src/conf.c
src/conf/Makefile.am
src/conf/alsa.conf
src/conf/alsa.conf.d/Makefile.am [new file with mode: 0644]
src/conf/alsa.conf.d/README [new file with mode: 0644]

index 7ee0ccc..13e38b8 100644 (file)
@@ -616,7 +616,8 @@ AC_OUTPUT(Makefile doc/Makefile doc/pictures/Makefile doc/doxygen.cfg \
          src/pcm/Makefile src/pcm/scopes/Makefile \
          src/rawmidi/Makefile src/timer/Makefile \
           src/hwdep/Makefile src/seq/Makefile src/ucm/Makefile \
-          src/compat/Makefile src/alisp/Makefile src/conf/Makefile \
+          src/compat/Makefile src/alisp/Makefile \
+         src/conf/Makefile src/conf/alsa.conf.d/Makefile \
          src/conf/cards/Makefile \
          src/conf/pcm/Makefile \
          modules/Makefile modules/mixer/Makefile modules/mixer/simple/Makefile \
index ddefff6..5b1b5a6 100644 (file)
@@ -417,6 +417,7 @@ beginning:</P>
 #include <stdarg.h>
 #include <limits.h>
 #include <sys/stat.h>
+#include <dirent.h>
 #include <locale.h>
 #include "local.h"
 #ifdef HAVE_LIBPTHREAD
@@ -3373,6 +3374,42 @@ static int snd_config_hooks(snd_config_t *config, snd_config_t *private_data)
        return err;
 }
 
+static int config_filename_filter(const struct dirent *dirent)
+{
+       size_t flen;
+
+       if (dirent == NULL)
+               return 0;
+       if (dirent->d_type == DT_DIR)
+               return 0;
+
+       flen = strlen(dirent->d_name);
+       if (flen <= 5)
+               return 0;
+
+       if (strncmp(&dirent->d_name[flen-5], ".conf", 5) == 0)
+               return 1;
+
+       return 0;
+}
+
+static int config_file_open(snd_config_t *root, const char *filename)
+{
+       snd_input_t *in;
+       int err;
+
+       err = snd_input_stdio_open(&in, filename, "r");
+       if (err >= 0) {
+               err = snd_config_load(root, in);
+               snd_input_close(in);
+               if (err < 0)
+                       SNDERR("%s may be old or corrupted: consider to remove or fix it", filename);
+       } else
+               SNDERR("cannot access file %s", filename);
+
+       return err;
+}
+
 /**
  * \brief Loads and parses the given configurations files.
  * \param[in] root Handle to the root configuration node.
@@ -3457,20 +3494,39 @@ int snd_config_hook_load(snd_config_t *root, snd_config_t *config, snd_config_t
                }
        } while (hit);
        for (idx = 0; idx < fi_count; idx++) {
-               snd_input_t *in;
+               struct stat st;
                if (!errors && access(fi[idx].name, R_OK) < 0)
                        continue;
-               err = snd_input_stdio_open(&in, fi[idx].name, "r");
-               if (err >= 0) {
-                       err = snd_config_load(root, in);
-                       snd_input_close(in);
-                       if (err < 0) {
-                               SNDERR("%s may be old or corrupted: consider to remove or fix it", fi[idx].name);
-                               goto _err;
-                       }
-               } else {
-                       SNDERR("cannot access file %s", fi[idx].name);
+               if (stat(fi[idx].name, &st) < 0) {
+                       SNDERR("cannot stat file/directory %s", fi[idx].name);
+                       continue;
                }
+               if (S_ISDIR(st.st_mode)) {
+                       struct dirent **namelist;
+                       int n;
+
+                       n = scandir(fi[idx].name, &namelist, config_filename_filter, versionsort);
+                       if (n > 0) {
+                               int j;
+                               err = 0;
+                               for (j = 0; j < n; ++j) {
+                                       if (err >= 0) {
+                                               int sl = strlen(fi[idx].name) + strlen(namelist[j]->d_name) + 2;
+                                               char *filename = malloc(sl);
+                                               snprintf(filename, sl, "%s/%s", fi[idx].name, namelist[j]->d_name);
+                                               filename[sl-1] = '\0';
+
+                                               err = config_file_open(root, filename);
+                                               free(filename);
+                                       }
+                                       free(namelist[j]);
+                               }
+                               free(namelist);
+                               if (err < 0)
+                                       goto _err;
+                       }
+               } else if (config_file_open(root, fi[idx].name) < 0)
+                       goto _err;
        }
        *dst = NULL;
        err = 0;
index 2e5d0bf..456454f 100644 (file)
@@ -1,4 +1,4 @@
-SUBDIRS=cards pcm
+SUBDIRS=cards pcm alsa.conf.d
 
 cfg_files = alsa.conf
 if BUILD_ALISP
index a33c24e..bc91df3 100644 (file)
@@ -8,6 +8,13 @@
        {
                func load
                files [
+                       {
+                               @func concat
+                               strings [
+                                       { @func datadir }
+                                       "/alsa.conf.d/"
+                               ]
+                       }
                        "/etc/asound.conf"
                        "~/.asoundrc"
                ]
diff --git a/src/conf/alsa.conf.d/Makefile.am b/src/conf/alsa.conf.d/Makefile.am
new file mode 100644 (file)
index 0000000..c91661e
--- /dev/null
@@ -0,0 +1,8 @@
+alsaconfigdir = @ALSA_CONFIG_DIR@
+alsadir = $(alsaconfigdir)/alsa.conf.d
+cfg_files = README
+
+alsa_DATA = $(cfg_files)
+
+EXTRA_DIST = \
+       $(cfg_files)
diff --git a/src/conf/alsa.conf.d/README b/src/conf/alsa.conf.d/README
new file mode 100644 (file)
index 0000000..9997884
--- /dev/null
@@ -0,0 +1,2 @@
+You can place files named *.conf in this folder and they will be processed
+when initialising alsa-lib.