]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
core: fix writing of ExecStartEx and friends
authorZbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl>
Mon, 3 Apr 2023 11:56:18 +0000 (13:56 +0200)
committerZbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl>
Mon, 24 Apr 2023 08:02:30 +0000 (10:02 +0200)
The property name is called ExecStartEx, but we have to write it as ExecStart=
in the unit file. :(
Bug introduced in b3d593673c5b8b0b7d781fd26ab2062ca6e7dbdb when ex-properties
were initially added.

In addition, we cannot escape $ as $$, because when ":" is used, we wouldn't
unescape $$ back to $.

src/core/dbus-execute.c
src/core/dbus-service.c

index 88be591fe8b05b63655cd5106e843fb6398e0e4e..6ad1d6b5fe50949399eb278a48b69fd3fa794f8e 100644 (file)
@@ -1516,6 +1516,9 @@ int bus_set_transient_exec_command(
         unsigned n = 0;
         int r;
 
+        /* Drop Ex from the written setting. E.g. ExecStart=, not ExecStartEx=. */
+        const char *written_name = is_ex_prop ? strndupa(name, strlen(name) - 2) : name;
+
         r = sd_bus_message_enter_container(message, 'a', is_ex_prop ? "(sasas)" : "(sasb)");
         if (r < 0)
                 return r;
@@ -1597,31 +1600,32 @@ int bus_set_transient_exec_command(
                 if (!f)
                         return -ENOMEM;
 
-                fprintf(f, "%s=\n", name);
+                fprintf(f, "%s=\n", written_name);
 
                 LIST_FOREACH(command, c, *exec_command) {
                         _cleanup_free_ char *a = NULL, *exec_chars = NULL;
+                        UnitWriteFlags esc_flags = UNIT_ESCAPE_SPECIFIERS |
+                                (FLAGS_SET(c->flags, EXEC_COMMAND_NO_ENV_EXPAND) ? UNIT_ESCAPE_EXEC_SYNTAX : UNIT_ESCAPE_EXEC_SYNTAX_ENV);
 
                         exec_chars = exec_command_flags_to_exec_chars(c->flags);
                         if (!exec_chars)
                                 return -ENOMEM;
 
-                        a = unit_concat_strv(c->argv, UNIT_ESCAPE_SPECIFIERS|UNIT_ESCAPE_EXEC_SYNTAX_ENV);
+                        a = unit_concat_strv(c->argv, esc_flags);
                         if (!a)
                                 return -ENOMEM;
 
                         if (streq_ptr(c->path, c->argv ? c->argv[0] : NULL))
-                                fprintf(f, "%s=%s%s\n", name, exec_chars, a);
+                                fprintf(f, "%s=%s%s\n", written_name, exec_chars, a);
                         else {
                                 _cleanup_free_ char *t = NULL;
                                 const char *p;
 
-                                p = unit_escape_setting(c->path,
-                                                        UNIT_ESCAPE_SPECIFIERS|UNIT_ESCAPE_EXEC_SYNTAX_ENV, &t);
+                                p = unit_escape_setting(c->path, esc_flags, &t);
                                 if (!p)
                                         return -ENOMEM;
 
-                                fprintf(f, "%s=%s@%s %s\n", name, exec_chars, p, a);
+                                fprintf(f, "%s=%s@%s %s\n", written_name, exec_chars, p, a);
                         }
                 }
 
@@ -1629,7 +1633,7 @@ int bus_set_transient_exec_command(
                 if (r < 0)
                         return r;
 
-                unit_write_setting(u, flags, name, buf);
+                unit_write_setting(u, flags, written_name, buf);
         }
 
         return 1;
index 0f6e3152330d07ba9624250247567312f6b92937..ff61495c34f78553adbe95e22bf162eed19bb12c 100644 (file)
@@ -635,7 +635,8 @@ static int bus_service_set_transient_property(
                 return bus_set_transient_exit_status(u, name, &s->success_status, message, flags, error);
 
         ci = service_exec_command_from_string(name);
-        ci = (ci >= 0) ? ci : service_exec_ex_command_from_string(name);
+        if (ci < 0)
+                ci = service_exec_ex_command_from_string(name);
         if (ci >= 0)
                 return bus_set_transient_exec_command(u, name, &s->exec_command[ci], message, flags, error);