summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--man/systemd-activate.xml14
-rw-r--r--src/activate/activate.c33
2 files changed, 43 insertions, 4 deletions
diff --git a/man/systemd-activate.xml b/man/systemd-activate.xml
index a5cab8e3b7..b62cf44ec4 100644
--- a/man/systemd-activate.xml
+++ b/man/systemd-activate.xml
@@ -99,7 +99,7 @@ along with systemd; If not, see <http://www.gnu.org/licenses/>.
</varlistentry>
<varlistentry>
- <term><option>-l</option></term>
+ <term><option>-l <replaceable>address</replaceable></option></term>
<term><option>--listen=<replaceable>address</replaceable></option></term>
<listitem><para>Listen on this <replaceable>address</replaceable>.
@@ -116,6 +116,18 @@ along with systemd; If not, see <http://www.gnu.org/licenses/>.
connection and pass the connection socket as standard input
and standard output.</para></listitem>
</varlistentry>
+
+ <varlistentry>
+ <term><option>-E <replaceable>VAR</replaceable><optional>=<replaceable>VALUE</replaceable></optional></option></term>
+ <term><option>--environment=<replaceable>VAR</replaceable><optional>=<replaceable>VALUE</replaceable></optional></option></term>
+
+ <listitem><para>Add this variable to the environment of the
+ launched process. If <replaceable>VAR</replaceable> is
+ followed by <literal>=</literal> assume that it is a
+ variable–value pair. Otherwise obtain the value from the
+ environment of <command>systemd-activate</command> itself.
+ </para></listitem>
+ </varlistentry>
</variablelist>
</refsect1>
diff --git a/src/activate/activate.c b/src/activate/activate.c
index 7fcb0a97c4..be40be48a4 100644
--- a/src/activate/activate.c
+++ b/src/activate/activate.c
@@ -38,6 +38,7 @@
static char** arg_listen = NULL;
static bool arg_accept = false;
static char** arg_args = NULL;
+static char** arg_environ = NULL;
static int add_epoll(int epoll_fd, int fd) {
int r;
@@ -164,12 +165,29 @@ static int open_sockets(int *epoll_fd, bool accept) {
}
static int launch(char* name, char **argv, char **environ, int fds) {
- unsigned n_env = 0;
- char* envp[7] = {NULL}; /* PATH, TERM, HOME, USER, LISTEN_FDS, LISTEN_PID */
+ unsigned n_env = 0, length;
+ char **envp = NULL, **s;
static const char* tocopy[] = {"TERM=", "PATH=", "USER=", "HOME="};
char _cleanup_free_ *tmp = NULL;
unsigned i;
+ length = strv_length(arg_environ);
+ /* PATH, TERM, HOME, USER, LISTEN_FDS, LISTEN_PID, NULL */
+ envp = new(char *, length + 7);
+
+ STRV_FOREACH(s, arg_environ) {
+ if (strchr(*s, '='))
+ envp[n_env++] = *s;
+ else {
+ char _cleanup_free_ *p = strappend(*s, "=");
+ if (!p)
+ return log_oom();
+ envp[n_env] = strv_find_prefix(environ, p);
+ if (envp[n_env])
+ n_env ++;
+ }
+ }
+
for (i = 0; i < ELEMENTSOF(tocopy); i++) {
envp[n_env] = strv_find_prefix(environ, tocopy[i]);
if (envp[n_env])
@@ -312,6 +330,7 @@ static int parse_argv(int argc, char *argv[]) {
{ "version", no_argument, NULL, ARG_VERSION },
{ "listen", required_argument, NULL, 'l' },
{ "accept", no_argument, NULL, 'a' },
+ { "environment", required_argument, NULL, 'E' },
{ NULL, 0, NULL, 0 }
};
@@ -320,7 +339,7 @@ static int parse_argv(int argc, char *argv[]) {
assert(argc >= 0);
assert(argv);
- while ((c = getopt_long(argc, argv, "+hl:sa", options, NULL)) >= 0)
+ while ((c = getopt_long(argc, argv, "+hl:saE:", options, NULL)) >= 0)
switch(c) {
case 'h':
help();
@@ -343,6 +362,14 @@ static int parse_argv(int argc, char *argv[]) {
arg_accept = true;
break;
+ case 'E': {
+ int r = strv_extend(&arg_environ, optarg);
+ if (r < 0)
+ return r;
+
+ break;
+ }
+
case '?':
return -EINVAL;