diff options
author | Zbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl> | 2014-12-09 14:41:24 -0500 |
---|---|---|
committer | Zbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl> | 2014-12-09 21:47:53 -0500 |
commit | a644abed54bd4a42ebe2c99af5cc621ffbaf6c55 (patch) | |
tree | 9770099429144daa24cde7f33dbf788be2ec67d7 /src | |
parent | 4dfb18922d5d1efb13ee459cbf23832277f85ed7 (diff) |
systemctl: fix invalid free when enabling sysv services fails
The error was introduced in v215-343-g60731f32f1 'systemctl: do not
bother to mutate state on error', by causing strv_free to attempt to
free a static string. Simplify the whole thing by always keeping the
array in valid state.
Diffstat (limited to 'src')
-rw-r--r-- | src/systemctl/systemctl.c | 22 |
1 files changed, 6 insertions, 16 deletions
diff --git a/src/systemctl/systemctl.c b/src/systemctl/systemctl.c index 6e48671ee6..17dfff7887 100644 --- a/src/systemctl/systemctl.c +++ b/src/systemctl/systemctl.c @@ -5143,7 +5143,7 @@ static int enable_sysv_units(const char *verb, char **args) { int r = 0; #if defined(HAVE_SYSV_COMPAT) && defined(HAVE_CHKCONFIG) - unsigned f = 1, t = 1; + unsigned f = 0; _cleanup_lookup_paths_free_ LookupPaths paths = {}; if (arg_scope != UNIT_FILE_SYSTEM) @@ -5162,7 +5162,7 @@ static int enable_sysv_units(const char *verb, char **args) { return r; r = 0; - for (f = 0; args[f]; f++) { + while (args[f]) { const char *name; _cleanup_free_ char *p = NULL, *q = NULL, *l = NULL; bool found_native = false, found_sysv; @@ -5173,7 +5173,7 @@ static int enable_sysv_units(const char *verb, char **args) { pid_t pid; siginfo_t status; - name = args[f]; + name = args[f++]; if (!endswith(name, ".service")) continue; @@ -5205,9 +5205,6 @@ static int enable_sysv_units(const char *verb, char **args) { if (!found_sysv) continue; - /* Mark this entry, so that we don't try enabling it as native unit */ - args[f] = (char*) ""; - log_info("%s is not a native service, redirecting to /sbin/chkconfig.", name); if (!isempty(arg_root)) @@ -5256,19 +5253,12 @@ static int enable_sysv_units(const char *verb, char **args) { return -EINVAL; } else return -EPROTO; - } - - /* Drop all SysV units */ - for (f = 0, t = 0; args[f]; f++) { - if (isempty(args[f])) - continue; - - args[t++] = args[f]; + /* Remove this entry, so that we don't try enabling it as native unit */ + assert(f > 0 && streq(args[f-1], name)); + assert_se(strv_remove(args + f - 1, name)); } - args[t] = NULL; - #endif return r; } |