diff options
-rw-r--r-- | src/core/load-dropin.c | 69 | ||||
-rw-r--r-- | src/shared/strv.c | 15 | ||||
-rw-r--r-- | src/shared/strv.h | 1 |
3 files changed, 57 insertions, 28 deletions
diff --git a/src/core/load-dropin.c b/src/core/load-dropin.c index 8e10d8fb4c..d53e77f706 100644 --- a/src/core/load-dropin.c +++ b/src/core/load-dropin.c @@ -29,24 +29,25 @@ #include "unit-name.h" #include "conf-parser.h" #include "load-fragment.h" +#include "conf-files.h" -static int load_dropin_config_file(Unit *u, const char *path) { - assert(u); - assert(path); - - if (!endswith(path, ".conf")) - return 0; - - return config_parse(path, NULL, UNIT_VTABLE(u)->sections, config_item_perf_lookup, (void*) load_fragment_gperf_lookup, false, u); -} - -static int iterate_dir(Unit *u, const char *path, UnitDependency dependency) { +static int iterate_dir(Unit *u, const char *path, UnitDependency dependency, char ***strv) { _cleanup_closedir_ DIR *d = NULL; int r; assert(u); assert(path); + /* The config directories are special, since the order of the + * drop-ins matters */ + if (dependency < 0) { + r = strv_extend(strv, path); + if (r < 0) + return log_oom(); + + return 0; + } + d = opendir(path); if (!d) { if (errno == ENOENT) @@ -77,21 +78,15 @@ static int iterate_dir(Unit *u, const char *path, UnitDependency dependency) { if (!f) return log_oom(); - if (dependency >= 0) { - r = unit_add_dependency_by_name(u, dependency, de->d_name, f, true); - if (r < 0) - log_error("Cannot add dependency %s to %s, ignoring: %s", de->d_name, u->id, strerror(-r)); - } else { - r = load_dropin_config_file(u, f); - if (r < 0) - log_error("Cannot load drop-in configuration file %s for %s, ignoring: %s", f, u->id, strerror(-r)); - } + r = unit_add_dependency_by_name(u, dependency, de->d_name, f, true); + if (r < 0) + log_error("Cannot add dependency %s to %s, ignoring: %s", de->d_name, u->id, strerror(-r)); } return 0; } -static int process_dir(Unit *u, const char *unit_path, const char *name, const char *suffix, UnitDependency dependency) { +static int process_dir(Unit *u, const char *unit_path, const char *name, const char *suffix, UnitDependency dependency, char ***strv) { int r; char *path; @@ -108,7 +103,7 @@ static int process_dir(Unit *u, const char *unit_path, const char *name, const c !set_get(u->manager->unit_path_cache, path)) r = 0; else - r = iterate_dir(u, path, dependency); + r = iterate_dir(u, path, dependency, strv); free(path); if (r < 0) @@ -132,7 +127,7 @@ static int process_dir(Unit *u, const char *unit_path, const char *name, const c !set_get(u->manager->unit_path_cache, path)) r = 0; else - r = iterate_dir(u, path, dependency); + r = iterate_dir(u, path, dependency, strv); free(path); if (r < 0) @@ -145,6 +140,9 @@ static int process_dir(Unit *u, const char *unit_path, const char *name, const c int unit_load_dropin(Unit *u) { Iterator i; char *t; + _cleanup_strv_free_ char **strv = NULL; + int r; + assert(u); @@ -154,22 +152,37 @@ int unit_load_dropin(Unit *u) { char **p; STRV_FOREACH(p, u->manager->lookup_paths.unit_path) { - int r; - - r = process_dir(u, *p, t, ".wants", UNIT_WANTS); + r = process_dir(u, *p, t, ".wants", UNIT_WANTS, NULL); if (r < 0) return r; - r = process_dir(u, *p, t, ".requires", UNIT_REQUIRES); + r = process_dir(u, *p, t, ".requires", UNIT_REQUIRES, NULL); if (r < 0) return r; /* This loads the drop-in config snippets */ - r = process_dir(u, *p, t, ".d", _UNIT_TYPE_INVALID); + r = process_dir(u, *p, t, ".d", _UNIT_DEPENDENCY_INVALID, &strv); if (r < 0) return r; } } + if (!strv_isempty(strv)) { + _cleanup_strv_free_ char **files = NULL, **f; + + r = conf_files_list_strv(&files, ".conf", (const char**) strv); + if (r < 0) { + log_error("Failed to get list of configuration files: %s", strerror(-r)); + return r; + } + + STRV_FOREACH(f, files) { + r = config_parse(*f, NULL, UNIT_VTABLE(u)->sections, config_item_perf_lookup, (void*) load_fragment_gperf_lookup, false, u); + if (r < 0) + return r; + } + } + + return 0; } diff --git a/src/shared/strv.c b/src/shared/strv.c index 6b76d0eaef..aed45d2612 100644 --- a/src/shared/strv.c +++ b/src/shared/strv.c @@ -370,6 +370,21 @@ fail: return NULL; } +int strv_extend(char ***l, const char *value) { + char **c; + + if (!value) + return 0; + + c = strv_append(*l, value); + if (!c) + return -ENOMEM; + + strv_free(*l); + *l = c; + return 0; +} + char **strv_uniq(char **l) { char **i; diff --git a/src/shared/strv.h b/src/shared/strv.h index 45558d8960..44ba3d1530 100644 --- a/src/shared/strv.h +++ b/src/shared/strv.h @@ -37,6 +37,7 @@ unsigned strv_length(char **l); char **strv_merge(char **a, char **b); char **strv_merge_concat(char **a, char **b, const char *suffix); char **strv_append(char **l, const char *s); +int strv_extend(char ***l, const char *value); char **strv_remove(char **l, const char *s); char **strv_remove_prefix(char **l, const char *s); |