diff options
Diffstat (limited to 'src/lib/fs/path.c')
-rw-r--r-- | src/lib/fs/path.c | 20 |
1 files changed, 18 insertions, 2 deletions
diff --git a/src/lib/fs/path.c b/src/lib/fs/path.c index c2fdddb9db..81960bd69a 100644 --- a/src/lib/fs/path.c +++ b/src/lib/fs/path.c @@ -571,6 +571,19 @@ wrap_closedir(void *arg) { closedir(arg); } + +/** Function passed to glob to handle processing errors. <b>epath</b> is the + * path that caused the error and <b>eerrno</b> is the errno set by the + * function that failed. We want to ignore ENOENT and ENOTDIR because, in BSD + * systems, these are not ignored automatically, which makes glob fail when + * globs expand to non-existing paths and GLOB_ERR is set. + */ +static int +glob_errfunc(const char *epath, int eerrno) +{ + (void)epath; + return eerrno == ENOENT || eerrno == ENOTDIR ? 0 : -1; +} #endif /* defined(HAVE_GLOB) */ /** Return a new list containing the paths that match the pattern @@ -591,7 +604,7 @@ tor_glob(const char *pattern) tor_free(pattern_normalized); #elif HAVE_GLOB /* !(defined(_WIN32)) */ glob_t matches; - int flags = GLOB_ERR | GLOB_NOSORT; + int flags = GLOB_NOSORT; #ifdef GLOB_ALTDIRFUNC /* use functions that call sandbox_intern_string */ flags |= GLOB_ALTDIRFUNC; @@ -604,7 +617,10 @@ tor_glob(const char *pattern) matches.gl_stat = &prot_stat; matches.gl_lstat = &prot_lstat; #endif /* defined(GLOB_ALTDIRFUNC) */ - int ret = glob(pattern, flags, NULL, &matches); + // use custom error handler to workaround BSD quirks and do not set GLOB_ERR + // because it would make glob fail on error even if the error handler ignores + // the error + int ret = glob(pattern, flags, glob_errfunc, &matches); if (ret == GLOB_NOMATCH) { return smartlist_new(); } else if (ret != 0) { |