[fuchsia] fix environment variable setup
Bug: US-562 #comment environment variables are set
Bug: CONN-18 #comment ssh now sets SSH_ vars that contain connection (and scope) info. which may be used to address local interface selection challenges.
Change-Id: I8c518ff39a3e0734210e271648516a0c85cea0b1
diff --git a/fuchsia/config.h b/fuchsia/config.h
index 5d3da60..3bb476b 100644
--- a/fuchsia/config.h
+++ b/fuchsia/config.h
@@ -1654,7 +1654,7 @@
/* #undef UNIXWARE_LONG_PASSWORDS */
/* Specify default $PATH */
-#define USER_PATH "/pkg/bin:/boot/bin:/system/bin"
+#define USER_PATH "/bin:/pkg/bin:/boot/bin:/system/bin"
/* Define this if you want to use libkafs' AFS support */
/* #undef USE_AFS */
diff --git a/fuchsia/fuchsia-compat.c b/fuchsia/fuchsia-compat.c
index e41c20d..d6e56c1 100644
--- a/fuchsia/fuchsia-compat.c
+++ b/fuchsia/fuchsia-compat.c
@@ -311,7 +311,8 @@
return pip[1];
}
-pid_t fuchsia_launch_child(const char* command, int in, int out, int err, bool transform) {
+// Note: **env is consumed by this function and will be freed.
+pid_t fuchsia_launch_child(const char* command, char** env, int in, int out, int err, bool transform) {
const char* argv[ARGV_MAX];
int argc = 1;
argv[0] = "/boot/bin/sh";
@@ -374,8 +375,15 @@
zx_handle_t proc = 0;
char err_msg[FDIO_SPAWN_ERR_MSG_MAX_LENGTH];
- uint32_t flags = FDIO_SPAWN_CLONE_ENVIRON | FDIO_SPAWN_CLONE_JOB | FDIO_SPAWN_CLONE_NAMESPACE;
- status = fdio_spawn_etc(ZX_HANDLE_INVALID, flags, argv[0], argv, NULL, 4, actions, &proc, err_msg);
+ uint32_t flags = FDIO_SPAWN_CLONE_JOB | FDIO_SPAWN_CLONE_NAMESPACE;
+ status = fdio_spawn_etc(ZX_HANDLE_INVALID, flags, argv[0], argv, (const char* const *)env, 4, actions, &proc, err_msg);
+ // env is constructed in session.c by child_set_env that always printf's new values and callocs the list pointer.
+ // walk each member, freeing them, then free the list.
+ char **envf = env;
+ while(*envf != NULL) {
+ free(*envf++);
+ }
+ free(env);
if (status < 0) {
fprintf(stderr, "error from fdio_spawn_etc: %s\n", err_msg);
diff --git a/fuchsia/fuchsia-compat.h b/fuchsia/fuchsia-compat.h
index 5302c0f..3b0f6bb 100644
--- a/fuchsia/fuchsia-compat.h
+++ b/fuchsia/fuchsia-compat.h
@@ -10,7 +10,9 @@
void fuchsia_init_async(void);
int chroot(const char *path);
-int fuchsia_launch_child(const char *command, int in, int out, int err, bool transform);
+
+// Note: char** env is consumed by this function and will be freed.
+int fuchsia_launch_child(const char* command, char** env, int in, int out, int err, bool transform);
/* This implements the subset of select() functionality used by openssh */
/* Uses void* instead of fd_set* for the read/write fd sets since this compat header is included in
diff --git a/session.c b/session.c
index 14ea1cc..8a2c20f 100644
--- a/session.c
+++ b/session.c
@@ -384,6 +384,17 @@
}
#define USE_PIPES 1
+
+// Fuchsia change, this function is defined below (and left there in order to ease merges from upstream).
+// This function is made available for the Fuchsia port, as we do not fork (and
+// later run do_setup_env in the child), instead we must use this function to
+// generate the new environment and pass it to fuchsia_launch_child.
+// This function allocates the char**, which is a nullptr terminated list of environment variables.
+#ifdef __Fuchsia__
+static char **
+do_setup_env(struct ssh *ssh, Session *s, const char *shell);
+#endif
+
/*
* This is called to fork and execute a command when we have no tty. This
* will call do_child from the child, and server_loop from the parent after
@@ -442,7 +453,8 @@
session_proctitle(s);
#ifdef __Fuchsia__
- pid = fuchsia_launch_child(command, pin[0], pout[1], perr[1], false);
+ char** env = do_setup_env(ssh, s, "");
+ pid = fuchsia_launch_child(command, env, pin[0], pout[1], perr[1], false);
if (pid <= 0) {
#ifdef USE_PIPES
close(pin[0]);
@@ -616,7 +628,8 @@
}
#ifdef __Fuchsia__
- pid = fuchsia_launch_child(command, ttyfd, ttyfd, ttyfd, true);
+ char** env = do_setup_env(ssh, s, "");
+ pid = fuchsia_launch_child(command, env, ttyfd, ttyfd, ttyfd, true);
#else
/* Fork the child. */