From: Florian Forster Date: Mon, 11 Feb 2008 11:01:06 +0000 (+0100) Subject: src/configfile.c: Use wordexp(3) to expand shell wildcards if available. X-Git-Tag: collectd-4.3.0beta1~3 X-Git-Url: https://git.verplant.org/?a=commitdiff_plain;h=23f2ac0835c5cf2760bd1b687e868fd033c7639c;p=collectd.git src/configfile.c: Use wordexp(3) to expand shell wildcards if available. --- diff --git a/configure.in b/configure.in index 04ba0f86..f59fc6b0 100644 --- a/configure.in +++ b/configure.in @@ -311,7 +311,7 @@ AC_CHECK_HEADERS(linux/un.h, [], [], #endif ]) -AC_CHECK_HEADERS(pwd.h grp.h sys/un.h ctype.h limits.h sys/quota.h xfs/xqm.h fs_info.h fshelp.h paths.h mntent.h mnttab.h sys/fstyp.h sys/fs_types.h sys/mntent.h sys/mnttab.h sys/statfs.h sys/statvfs.h sys/vfs.h sys/vfstab.h kvm.h) +AC_CHECK_HEADERS(pwd.h grp.h sys/un.h ctype.h limits.h sys/quota.h xfs/xqm.h fs_info.h fshelp.h paths.h mntent.h mnttab.h sys/fstyp.h sys/fs_types.h sys/mntent.h sys/mnttab.h sys/statfs.h sys/statvfs.h sys/vfs.h sys/vfstab.h kvm.h wordexp.h) # For the dns plugin AC_CHECK_HEADERS(arpa/nameser.h) diff --git a/src/configfile.c b/src/configfile.c index 3b6cb6b3..36b6dadc 100644 --- a/src/configfile.c +++ b/src/configfile.c @@ -30,6 +30,10 @@ #include "types_list.h" #include "utils_threshold.h" +#if HAVE_WORDEXP_H +# include +#endif /* HAVE_WORDEXP_H */ + #define ESCAPE_NULL(str) ((str) == NULL ? "(null)" : (str)) /* @@ -546,11 +550,20 @@ static oconfig_item_t *cf_read_dir (const char *dir, int depth) * * Path is stat'ed and either cf_read_file or cf_read_dir is called * accordingly. + * + * There are two versions of this function: If `wordexp' exists shell wildcards + * will be expanded and the function will include all matches found. If + * `wordexp' (or, more precisely, it's header file) is not available the + * simpler function is used which does not do any such expansion. */ +#if HAVE_WORDEXP_H static oconfig_item_t *cf_read_generic (const char *path, int depth) { - struct stat statbuf; + oconfig_item_t *root = NULL; int status; + const char *path_ptr; + wordexp_t we; + int i; if (depth >= CF_MAX_DEPTH) { @@ -559,7 +572,72 @@ static oconfig_item_t *cf_read_generic (const char *path, int depth) return (NULL); } - fprintf (stderr, "cf_read_generic (path = %s, depth = %i);", path, depth); + status = wordexp (path, &we, WRDE_NOCMD); + if (status != 0) + { + ERROR ("configfile: wordexp (%s) failed.", path); + return (NULL); + } + + root = (oconfig_item_t *) malloc (sizeof (oconfig_item_t)); + if (root == NULL) + { + ERROR ("configfile: malloc failed."); + return (NULL); + } + memset (root, '\0', sizeof (oconfig_item_t)); + + for (i = 0; i < we.we_wordc; i++) + { + oconfig_item_t *temp; + struct stat statbuf; + + path_ptr = we.we_wordv[i]; + + status = stat (path_ptr, &statbuf); + if (status != 0) + { + char errbuf[1024]; + ERROR ("configfile: stat (%s) failed: %s", + path_ptr, + sstrerror (errno, errbuf, sizeof (errbuf))); + return (NULL); + } + + if (S_ISREG (statbuf.st_mode)) + temp = cf_read_file (path_ptr, depth); + else if (S_ISDIR (statbuf.st_mode)) + temp = cf_read_dir (path_ptr, depth); + else + { + ERROR ("configfile: %s is neither a file nor a " + "directory.", path); + continue; + } + + cf_ci_append_children (root, temp); + sfree (temp->children); + sfree (temp); + } + + wordfree (&we); + + return (root); +} /* oconfig_item_t *cf_read_generic */ +/* #endif HAVE_WORDEXP_H */ + +#else /* if !HAVE_WORDEXP_H */ +static oconfig_item_t *cf_read_generic (const char *path, int depth) +{ + struct stat statbuf; + int status; + + if (depth >= CF_MAX_DEPTH) + { + ERROR ("configfile: Not including `%s' because the maximum " + "nesting depth has been reached.", path); + return (NULL); + } status = stat (path, &statbuf); if (status != 0) @@ -579,6 +657,7 @@ static oconfig_item_t *cf_read_generic (const char *path, int depth) ERROR ("configfile: %s is neither a file nor a directory.", path); return (NULL); } /* oconfig_item_t *cf_read_generic */ +#endif /* !HAVE_WORDEXP_H */ /* * Public functions