]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
basic/escape: add mode where empty arguments are still shown as ""
authorZbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl>
Wed, 3 Mar 2021 12:40:51 +0000 (13:40 +0100)
committerZbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl>
Wed, 5 May 2021 10:12:10 +0000 (12:12 +0200)
For variables, FOO= is OK. But when quoting positional arguments, we want to
use something with quotes ("", '', or even $'') for an empty string.

src/basic/escape.c
src/basic/escape.h
src/test/test-escape.c

index 7a9a3b56166e905598292835a0b4711ae158aca5..2de275f04e1f2f121bbcff09d1042eb2d5254913 100644 (file)
@@ -504,6 +504,9 @@ char* shell_maybe_quote(const char *s, ShellEscapeFlags flags) {
          * string. Note that we treat benign UTF-8 characters as needing
          * escaping too, but that should be OK. */
 
+        if (FLAGS_SET(flags, SHELL_ESCAPE_EMPTY) && isempty(s))
+                return strdup("\"\""); /* We don't use $'' here in the POSIX mode. "" is fine too. */
+
         for (p = s; *p; p++)
                 if (*p <= ' ' ||
                     *p >= 127 ||
index 7ecae49e10d5a86228af4d6a2817e4c2072428e1..3cb107ae902cad47e29bb7df75f120847f0a6109 100644 (file)
@@ -38,6 +38,7 @@ typedef enum ShellEscapeFlags {
          * Tabs and newlines are escaped. */
 
         SHELL_ESCAPE_POSIX = 1 << 1, /* Use POSIX shell escape syntax (a string enclosed in $'') instead of plain quotes. */
+        SHELL_ESCAPE_EMPTY = 1 << 2, /* Format empty arguments as "". */
 } ShellEscapeFlags;
 
 char* cescape(const char *s);
index 1e6536884209f8543b5d3370c39e6b84a8bc4403..854a55174b98b1bcb8d0812e1a01f3b89b5945ab 100644 (file)
@@ -140,7 +140,9 @@ static void test_shell_maybe_quote_one(const char *s, ShellEscapeFlags flags, co
 static void test_shell_maybe_quote(void) {
 
         test_shell_maybe_quote_one("", 0, "");
+        test_shell_maybe_quote_one("", SHELL_ESCAPE_EMPTY, "\"\"");
         test_shell_maybe_quote_one("", SHELL_ESCAPE_POSIX, "");
+        test_shell_maybe_quote_one("", SHELL_ESCAPE_POSIX | SHELL_ESCAPE_EMPTY, "\"\"");
         test_shell_maybe_quote_one("\\", 0, "\"\\\\\"");
         test_shell_maybe_quote_one("\\", SHELL_ESCAPE_POSIX, "$'\\\\'");
         test_shell_maybe_quote_one("\"", 0, "\"\\\"\"");
@@ -156,7 +158,9 @@ static void test_shell_maybe_quote(void) {
         test_shell_maybe_quote_one("foo \"bar\" waldo", 0, "\"foo \\\"bar\\\" waldo\"");
         test_shell_maybe_quote_one("foo \"bar\" waldo", SHELL_ESCAPE_POSIX, "$'foo \"bar\" waldo'");
         test_shell_maybe_quote_one("foo$bar", 0, "\"foo\\$bar\"");
+        test_shell_maybe_quote_one("foo$bar", SHELL_ESCAPE_EMPTY, "\"foo\\$bar\"");
         test_shell_maybe_quote_one("foo$bar", SHELL_ESCAPE_POSIX, "$'foo$bar'");
+        test_shell_maybe_quote_one("foo$bar", SHELL_ESCAPE_POSIX | SHELL_ESCAPE_EMPTY, "$'foo$bar'");
 
         /* Note that current users disallow control characters, so this "test"
          * is here merely to establish current behaviour. If control characters