Adam Williamson 07b358
From 054d9609e1639a725e9a29af086c1585bacc43ff Mon Sep 17 00:00:00 2001
Adam Williamson 07b358
From: =?UTF-8?q?Zbigniew=20J=C4=99drzejewski-Szmek?= <zbyszek@in.waw.pl>
Adam Williamson 07b358
Date: Thu, 6 Aug 2015 21:34:15 -0400
Adam Williamson 07b358
Subject: [PATCH] manager: put bin before sbin for user instances
Adam Williamson 07b358
Adam Williamson 07b358
Traditionally, user logins had a $PATH in which /bin was before /sbin, while
Adam Williamson 07b358
root logins had a $PATH with /sbin first. This allows the tricks that
Adam Williamson 07b358
consolehelper is doing to work. But even if we ignore consolehelper, having the
Adam Williamson 07b358
path in this order might have been used by admins for other purposes, and
Adam Williamson 07b358
keeping the order in user sessions will make it easier the adoption of systemd
Adam Williamson 07b358
user sessions a bit easier.
Adam Williamson 07b358
Adam Williamson 07b358
Fixes #733.
Adam Williamson 07b358
https://bugzilla.redhat.com/show_bug.cgi?id=1744059
Adam Williamson 07b358
Adam Williamson 07b358
OOM handling in manager_default_environment wasn't really correct.
Adam Williamson 07b358
Now the (theorertical) malloc failure in strv_new() is handled.
Adam Williamson 07b358
Adam Williamson 07b358
Please note that this has no effect on:
Adam Williamson 07b358
- systems with merged /bin-/sbin (e.g. arch)
Adam Williamson 07b358
Adam Williamson 07b358
- when there are no binaries that differ between the two locations.
Adam Williamson 07b358
Adam Williamson 07b358
  E.g. on my F30 laptop there is exactly one program that is affected:
Adam Williamson 07b358
  /usr/bin/setup -> consolehelper.
Adam Williamson 07b358
Adam Williamson 07b358
  There is less and less stuff that relies on consolehelper, but there's still
Adam Williamson 07b358
  some.
Adam Williamson 07b358
Adam Williamson 07b358
So for "clean" systems this makes no difference, but helps with legacy setups.
Adam Williamson 07b358
Adam Williamson 07b358
$ dnf repoquery --releasever=31 --qf %{name} --whatrequires usermode
Adam Williamson 07b358
anaconda-live
Adam Williamson 07b358
audit-viewer
Adam Williamson 07b358
beesu
Adam Williamson 07b358
chkrootkit
Adam Williamson 07b358
driftnet
Adam Williamson 07b358
drobo-utils-gui
Adam Williamson 07b358
hddtemp
Adam Williamson 07b358
mate-system-log
Adam Williamson 07b358
mock
Adam Williamson 07b358
pure-ftpd
Adam Williamson 07b358
setuptool
Adam Williamson 07b358
subscription-manager
Adam Williamson 07b358
system-config-httpd
Adam Williamson 07b358
system-config-rootpassword
Adam Williamson 07b358
system-switch-java
Adam Williamson 07b358
system-switch-mail
Adam Williamson 07b358
usermode-gtk
Adam Williamson 07b358
vpnc-consoleuser
Adam Williamson 07b358
wifi-radar
Adam Williamson 07b358
xawtv
Adam Williamson 07b358
---
Adam Williamson 07b358
 man/systemd.exec.xml  | 35 +++++++++++++++++++++--------------
Adam Williamson 07b358
 src/basic/path-util.h |  8 ++++++++
Adam Williamson 07b358
 src/core/manager.c    | 23 +++++++++++++++++++----
Adam Williamson 07b358
 3 files changed, 48 insertions(+), 18 deletions(-)
Adam Williamson 07b358
Adam Williamson 07b358
diff --git a/man/systemd.exec.xml b/man/systemd.exec.xml
Adam Williamson 07b358
index fbbfd4f5146..5cb83afa578 100644
Adam Williamson 07b358
--- a/man/systemd.exec.xml
Adam Williamson 07b358
+++ b/man/systemd.exec.xml
Adam Williamson 07b358
@@ -2152,16 +2152,17 @@ StandardInputData=SWNrIHNpdHplIGRhIHVuJyBlc3NlIEtsb3BzLAp1ZmYgZWVtYWwga2xvcHAncy
Adam Williamson 07b358
       <varlistentry>
Adam Williamson 07b358
         <term><varname>LogExtraFields=</varname></term>
Adam Williamson 07b358
 
Adam Williamson 07b358
-        <listitem><para>Configures additional log metadata fields to include in all log records generated by processes
Adam Williamson 07b358
-        associated with this unit. This setting takes one or more journal field assignments in the format
Adam Williamson 07b358
-        <literal>FIELD=VALUE</literal> separated by whitespace. See
Adam Williamson 07b358
-        <citerefentry><refentrytitle>systemd.journal-fields</refentrytitle><manvolnum>7</manvolnum></citerefentry> for
Adam Williamson 07b358
-        details on the journal field concept. Even though the underlying journal implementation permits binary field
Adam Williamson 07b358
-        values, this setting accepts only valid UTF-8 values. To include space characters in a journal field value,
Adam Williamson 07b358
-        enclose the assignment in double quotes ("). The usual specifiers are expanded in all assignments (see
Adam Williamson 07b358
-        below). Note that this setting is not only useful for attaching additional metadata to log records of a unit,
Adam Williamson 07b358
-        but given that all fields and values are indexed may also be used to implement cross-unit log record
Adam Williamson 07b358
-        matching. Assign an empty string to reset the list.</para></listitem>
Adam Williamson 07b358
+        <listitem><para>Configures additional log metadata fields to include in all log records generated by
Adam Williamson 07b358
+        processes associated with this unit. This setting takes one or more journal field assignments in the
Adam Williamson 07b358
+        format <literal>FIELD=VALUE</literal> separated by whitespace. See
Adam Williamson 07b358
+        <citerefentry><refentrytitle>systemd.journal-fields</refentrytitle><manvolnum>7</manvolnum></citerefentry>
Adam Williamson 07b358
+        for details on the journal field concept. Even though the underlying journal implementation permits
Adam Williamson 07b358
+        binary field values, this setting accepts only valid UTF-8 values. To include space characters in a
Adam Williamson 07b358
+        journal field value, enclose the assignment in double quotes ("). 
Adam Williamson 07b358
+        The usual specifiers are expanded in all assignments (see below). Note that this setting is not only
Adam Williamson 07b358
+        useful for attaching additional metadata to log records of a unit, but given that all fields and
Adam Williamson 07b358
+        values are indexed may also be used to implement cross-unit log record matching. Assign an empty
Adam Williamson 07b358
+        string to reset the list.</para></listitem>
Adam Williamson 07b358
       </varlistentry>
Adam Williamson 07b358
 
Adam Williamson 07b358
       <varlistentry>
Adam Williamson 07b358
@@ -2355,10 +2356,16 @@ StandardInputData=SWNrIHNpdHplIGRhIHVuJyBlc3NlIEtsb3BzLAp1ZmYgZWVtYWwga2xvcHAncy
Adam Williamson 07b358
       <varlistentry>
Adam Williamson 07b358
         <term><varname>$PATH</varname></term>
Adam Williamson 07b358
 
Adam Williamson 07b358
-        <listitem><para>Colon-separated list of directories to use
Adam Williamson 07b358
-        when launching executables. systemd uses a fixed value of
Adam Williamson 07b358
-        <filename>/usr/local/sbin</filename>:<filename>/usr/local/bin</filename>:<filename>/usr/sbin</filename>:<filename>/usr/bin</filename>:<filename>/sbin</filename>:<filename>/bin</filename>.
Adam Williamson 07b358
-        </para></listitem>
Adam Williamson 07b358
+        <listitem><para>Colon-separated list of directories to use when launching
Adam Williamson 07b358
+        executables. <command>systemd</command> uses a fixed value of
Adam Williamson 07b358
+        <literal><filename>/usr/local/sbin</filename>:<filename>/usr/local/bin</filename>:<filename>/usr/sbin</filename>:<filename>/usr/bin</filename></literal>
Adam Williamson 07b358
+        in the system manager. When compiled for systems with "unmerged /usr" (<filename>/bin</filename> is
Adam Williamson 07b358
+        not a symlink to <filename>/usr/bin</filename>),
Adam Williamson 07b358
+        <literal>:<filename>/sbin</filename>:<filename>/bin</filename></literal> is appended. In case of the
Adam Williamson 07b358
+        the user manager, each <filename>bin/</filename> and <filename>sbin/</filename> pair is switched, so
Adam Williamson 07b358
+        that programs from <filename>/usr/bin</filename> have higher priority than programs from
Adam Williamson 07b358
+        <filename>/usr/sbin</filename>, etc. It is recommended to not rely on this in any way, and have only
Adam Williamson 07b358
+        one program with a given name in <varname>$PATH</varname>.</para></listitem>
Adam Williamson 07b358
       </varlistentry>
Adam Williamson 07b358
 
Adam Williamson 07b358
       <varlistentry>
Adam Williamson 07b358
diff --git a/src/basic/path-util.h b/src/basic/path-util.h
Adam Williamson 07b358
index 1f46cd65c96..71fb7041a3c 100644
Adam Williamson 07b358
--- a/src/basic/path-util.h
Adam Williamson 07b358
+++ b/src/basic/path-util.h
Adam Williamson 07b358
@@ -11,30 +11,38 @@
Adam Williamson 07b358
 #include "time-util.h"
Adam Williamson 07b358
 
Adam Williamson 07b358
 #define PATH_SPLIT_SBIN_BIN(x) x "sbin:" x "bin"
Adam Williamson 07b358
+#define PATH_SPLIT_BIN_SBIN(x) x "bin:" x "sbin"
Adam Williamson 07b358
 #define PATH_SPLIT_SBIN_BIN_NULSTR(x) x "sbin\0" x "bin\0"
Adam Williamson 07b358
 
Adam Williamson 07b358
 #define PATH_NORMAL_SBIN_BIN(x) x "bin"
Adam Williamson 07b358
+#define PATH_NORMAL_BIN_SBIN(x) x "bin"
Adam Williamson 07b358
 #define PATH_NORMAL_SBIN_BIN_NULSTR(x) x "bin\0"
Adam Williamson 07b358
 
Adam Williamson 07b358
 #if HAVE_SPLIT_BIN
Adam Williamson 07b358
 #  define PATH_SBIN_BIN(x) PATH_SPLIT_SBIN_BIN(x)
Adam Williamson 07b358
+#  define PATH_BIN_SBIN(x) PATH_SPLIT_BIN_SBIN(x)
Adam Williamson 07b358
 #  define PATH_SBIN_BIN_NULSTR(x) PATH_SPLIT_SBIN_BIN_NULSTR(x)
Adam Williamson 07b358
 #else
Adam Williamson 07b358
 #  define PATH_SBIN_BIN(x) PATH_NORMAL_SBIN_BIN(x)
Adam Williamson 07b358
+#  define PATH_BIN_SBIN(x) PATH_NORMAL_BIN_SBIN(x)
Adam Williamson 07b358
 #  define PATH_SBIN_BIN_NULSTR(x) PATH_NORMAL_SBIN_BIN_NULSTR(x)
Adam Williamson 07b358
 #endif
Adam Williamson 07b358
 
Adam Williamson 07b358
 #define DEFAULT_PATH_NORMAL PATH_SBIN_BIN("/usr/local/") ":" PATH_SBIN_BIN("/usr/")
Adam Williamson 07b358
+#define DEFAULT_USER_PATH_NORMAL PATH_BIN_SBIN("/usr/local/") ":" PATH_BIN_SBIN("/usr/")
Adam Williamson 07b358
 #define DEFAULT_PATH_NORMAL_NULSTR PATH_SBIN_BIN_NULSTR("/usr/local/") PATH_SBIN_BIN_NULSTR("/usr/")
Adam Williamson 07b358
 #define DEFAULT_PATH_SPLIT_USR DEFAULT_PATH_NORMAL ":" PATH_SBIN_BIN("/")
Adam Williamson 07b358
+#define DEFAULT_USER_PATH_SPLIT_USR DEFAULT_PATH_NORMAL ":" PATH_BIN_SBIN("/")
Adam Williamson 07b358
 #define DEFAULT_PATH_SPLIT_USR_NULSTR DEFAULT_PATH_NORMAL_NULSTR PATH_SBIN_BIN_NULSTR("/")
Adam Williamson 07b358
 #define DEFAULT_PATH_COMPAT PATH_SPLIT_SBIN_BIN("/usr/local/") ":" PATH_SPLIT_SBIN_BIN("/usr/") ":" PATH_SPLIT_SBIN_BIN("/")
Adam Williamson 07b358
 
Adam Williamson 07b358
 #if HAVE_SPLIT_USR
Adam Williamson 07b358
 #  define DEFAULT_PATH DEFAULT_PATH_SPLIT_USR
Adam Williamson 07b358
+#  define DEFAULT_USER_PATH DEFAULT_USER_PATH_SPLIT_USR
Adam Williamson 07b358
 #  define DEFAULT_PATH_NULSTR DEFAULT_PATH_SPLIT_USR_NULSTR
Adam Williamson 07b358
 #else
Adam Williamson 07b358
 #  define DEFAULT_PATH DEFAULT_PATH_NORMAL
Adam Williamson 07b358
+#  define DEFAULT_USER_PATH DEFAULT_USER_PATH_NORMAL
Adam Williamson 07b358
 #  define DEFAULT_PATH_NULSTR DEFAULT_PATH_NORMAL_NULSTR
Adam Williamson 07b358
 #endif
Adam Williamson 07b358
 
Adam Williamson 07b358
diff --git a/src/core/manager.c b/src/core/manager.c
Adam Williamson 07b358
index 8d691a19c3d..91a601e8fd8 100644
Adam Williamson 07b358
--- a/src/core/manager.c
Adam Williamson 07b358
+++ b/src/core/manager.c
Adam Williamson 07b358
@@ -603,6 +603,8 @@ static char** sanitize_environment(char **l) {
Adam Williamson 07b358
 }
Adam Williamson 07b358
 
Adam Williamson 07b358
 int manager_default_environment(Manager *m) {
Adam Williamson 07b358
+        int r;
Adam Williamson 07b358
+
Adam Williamson 07b358
         assert(m);
Adam Williamson 07b358
 
Adam Williamson 07b358
         m->transient_environment = strv_free(m->transient_environment);
Adam Williamson 07b358
@@ -616,16 +618,29 @@ int manager_default_environment(Manager *m) {
Adam Williamson 07b358
                  * /proc/self/environ valid; it is used for tagging
Adam Williamson 07b358
                  * the init process inside containers. */
Adam Williamson 07b358
                 m->transient_environment = strv_new("PATH=" DEFAULT_PATH);
Adam Williamson 07b358
+                if (!m->transient_environment)
Adam Williamson 07b358
+                        return log_oom();
Adam Williamson 07b358
 
Adam Williamson 07b358
                 /* Import locale variables LC_*= from configuration */
Adam Williamson 07b358
                 (void) locale_setup(&m->transient_environment);
Adam Williamson 07b358
-        } else
Adam Williamson 07b358
+        } else {
Adam Williamson 07b358
+                _cleanup_free_ char *k = NULL;
Adam Williamson 07b358
+
Adam Williamson 07b358
                 /* The user manager passes its own environment
Adam Williamson 07b358
-                 * along to its children. */
Adam Williamson 07b358
+                 * along to its children, except for $PATH. */
Adam Williamson 07b358
                 m->transient_environment = strv_copy(environ);
Adam Williamson 07b358
+                if (!m->transient_environment)
Adam Williamson 07b358
+                        return log_oom();
Adam Williamson 07b358
 
Adam Williamson 07b358
-        if (!m->transient_environment)
Adam Williamson 07b358
-                return log_oom();
Adam Williamson 07b358
+                k = strdup("PATH=" DEFAULT_USER_PATH);
Adam Williamson 07b358
+                if (!k)
Adam Williamson 07b358
+                        return log_oom();
Adam Williamson 07b358
+
Adam Williamson 07b358
+                r = strv_env_replace(&m->transient_environment, k);
Adam Williamson 07b358
+                if (r < 0)
Adam Williamson 07b358
+                        return log_oom();
Adam Williamson 07b358
+                TAKE_PTR(k);
Adam Williamson 07b358
+        }
Adam Williamson 07b358
 
Adam Williamson 07b358
         sanitize_environment(m->transient_environment);
Adam Williamson 07b358