[git commit master 1/1] use user's shell instead of hardwired "/bin/sh" (android needs this)

Denys Vlasenko vda.linux at googlemail.com
Tue Mar 8 20:02:42 UTC 2011


commit: http://git.busybox.net/busybox/commit/?id=681efe20d327e9e6774b174a617d66bbb9d21f48
branch: http://git.busybox.net/busybox/commit/?id=refs/heads/master

Signed-off-by: Denys Vlasenko <vda.linux at googlemail.com>
---
 archival/libarchive/data_extract_to_command.c |    8 ++++++--
 archival/tar.c                                |    1 +
 console-tools/openvt.c                        |    4 +---
 coreutils/chroot.c                            |    8 +++-----
 include/archive.h                             |    1 +
 include/libbb.h                               |    9 ++++++++-
 loginutils/adduser.c                          |    3 ++-
 miscutils/conspy.c                            |    4 +---
 miscutils/crontab.c                           |    7 ++++---
 networking/ifupdown.c                         |    9 +++++----
 runit/svlogd.c                                |    7 +++++--
 util-linux/script.c                           |    5 +----
 12 files changed, 38 insertions(+), 28 deletions(-)

diff --git a/archival/libarchive/data_extract_to_command.c b/archival/libarchive/data_extract_to_command.c
index 2bbab76..0e97704 100644
--- a/archival/libarchive/data_extract_to_command.c
+++ b/archival/libarchive/data_extract_to_command.c
@@ -99,8 +99,12 @@ void FAST_FUNC data_extract_to_command(archive_handle_t *archive_handle)
 			close(p[1]);
 			xdup2(p[0], STDIN_FILENO);
 			signal(SIGPIPE, SIG_DFL);
-			execl(DEFAULT_SHELL, DEFAULT_SHELL_SHORT_NAME, "-c", archive_handle->tar__to_command, NULL);
-			bb_perror_msg_and_die("can't execute '%s'", DEFAULT_SHELL);
+			execl(archive_handle->tar__to_command_shell,
+				archive_handle->tar__to_command_shell,
+				"-c",
+				archive_handle->tar__to_command,
+				NULL);
+			bb_perror_msg_and_die("can't execute '%s'", archive_handle->tar__to_command_shell);
 		}
 		close(p[0]);
 		/* Our caller is expected to do signal(SIGPIPE, SIG_IGN)
diff --git a/archival/tar.c b/archival/tar.c
index d43c8de..01b83d5 100644
--- a/archival/tar.c
+++ b/archival/tar.c
@@ -970,6 +970,7 @@ int tar_main(int argc UNUSED_PARAM, char **argv)
 		putenv((char*)"TAR_FILETYPE=f");
 		signal(SIGPIPE, SIG_IGN);
 		tar_handle->action_data = data_extract_to_command;
+		IF_FEATURE_TAR_TO_COMMAND(tar_handle->tar__to_command_shell = xstrdup(get_shell_name());)
 	}
 
 	if (opt & OPT_KEEP_OLD)
diff --git a/console-tools/openvt.c b/console-tools/openvt.c
index 6e0b589..56f50c6 100644
--- a/console-tools/openvt.c
+++ b/console-tools/openvt.c
@@ -144,9 +144,7 @@ int openvt_main(int argc UNUSED_PARAM, char **argv)
 
 	if (!argv[0]) {
 		argv--;
-		argv[0] = getenv("SHELL");
-		if (!argv[0])
-			argv[0] = (char *) DEFAULT_SHELL;
+		argv[0] = (char *) get_shell_name();
 		/*argv[1] = NULL; - already is */
 	}
 
diff --git a/coreutils/chroot.c b/coreutils/chroot.c
index b80a12e..5ac2e89 100644
--- a/coreutils/chroot.c
+++ b/coreutils/chroot.c
@@ -23,11 +23,9 @@ int chroot_main(int argc UNUSED_PARAM, char **argv)
 	++argv;
 	if (!*argv) { /* no 2nd param (PROG), use shell */
 		argv -= 2;
-		argv[0] = getenv("SHELL");
-		if (!argv[0]) {
-			argv[0] = (char *) DEFAULT_SHELL;
-		}
-		argv[1] = (char *) "-i";
+		argv[0] = (char *) get_shell_name();
+		argv[1] = (char *) "-i"; /* GNU coreutils 8.4 compat */
+		/*argv[2] = NULL; - already is */
 	}
 
 	BB_EXECVP_or_die(argv);
diff --git a/include/archive.h b/include/archive.h
index 181c187..b139dc5 100644
--- a/include/archive.h
+++ b/include/archive.h
@@ -84,6 +84,7 @@ typedef struct archive_handle_t {
 # endif
 #if ENABLE_FEATURE_TAR_TO_COMMAND
 	char* tar__to_command;
+	const char* tar__to_command_shell;
 #endif
 # if ENABLE_FEATURE_TAR_SELINUX
 	char* tar__global_sctx;
diff --git a/include/libbb.h b/include/libbb.h
index c26012c..c371e35 100644
--- a/include/libbb.h
+++ b/include/libbb.h
@@ -1198,10 +1198,17 @@ char *bb_simplify_path(const char *path) FAST_FUNC;
 /* Returns ptr to NUL */
 char *bb_simplify_abs_path_inplace(char *path) FAST_FUNC;
 
-#define FAIL_DELAY 3
+#define LOGIN_FAIL_DELAY 3
 extern void bb_do_delay(int seconds) FAST_FUNC;
 extern void change_identity(const struct passwd *pw) FAST_FUNC;
 extern void run_shell(const char *shell, int loginshell, const char *command, const char **additional_args) NORETURN FAST_FUNC;
+
+/* Returns $SHELL, getpwuid(getuid())->pw_shell, or DEFAULT_SHELL.
+ * Note that getpwuid result might need xstrdup'ing
+ * if there is a possibility of intervening getpwxxx() calls.
+ */
+const char *get_shell_name(void);
+
 #if ENABLE_SELINUX
 extern void renew_current_security_context(void) FAST_FUNC;
 extern void set_current_security_context(security_context_t sid) FAST_FUNC;
diff --git a/loginutils/adduser.c b/loginutils/adduser.c
index 9d3d9cb..0c675ca 100644
--- a/loginutils/adduser.c
+++ b/loginutils/adduser.c
@@ -132,7 +132,8 @@ int adduser_main(int argc UNUSED_PARAM, char **argv)
 	}
 
 	pw.pw_gecos = (char *)"Linux User,,,";
-	pw.pw_shell = (char *)DEFAULT_SHELL;
+	/* We assume that newly created users "inherit" root's shell setting */
+	pw.pw_shell = (char *)get_shell_name();
 	pw.pw_dir = NULL;
 
 	/* exactly one non-option arg */
diff --git a/miscutils/conspy.c b/miscutils/conspy.c
index 1fdb2fb..9c54053 100644
--- a/miscutils/conspy.c
+++ b/miscutils/conspy.c
@@ -316,10 +316,8 @@ static NOINLINE void start_shell_in_child(const char* tty_name)
 	int pid = xvfork();
 	if (pid == 0) {
 		struct termios termchild;
-		char *shell = getenv("SHELL");
+		const char *shell = get_shell_name();
 
-		if (!shell)
-			shell = (char *) DEFAULT_SHELL;
 		signal(SIGHUP, SIG_IGN);
 		// set tty as a controlling tty
 		setsid();
diff --git a/miscutils/crontab.c b/miscutils/crontab.c
index 163e15d..16d7fdf 100644
--- a/miscutils/crontab.c
+++ b/miscutils/crontab.c
@@ -20,8 +20,9 @@
 static void edit_file(const struct passwd *pas, const char *file)
 {
 	const char *ptr;
-	int pid = xvfork();
+	pid_t pid;
 
+	pid = xvfork();
 	if (pid) { /* parent */
 		wait4pid(pid);
 		return;
@@ -30,7 +31,7 @@ static void edit_file(const struct passwd *pas, const char *file)
 	/* CHILD - change user and run editor */
 	/* initgroups, setgid, setuid */
 	change_identity(pas);
-	setup_environment(DEFAULT_SHELL,
+	setup_environment(pas->pw_shell,
 			SETUP_ENV_CHANGEENV | SETUP_ENV_TO_TMP,
 			pas);
 	ptr = getenv("VISUAL");
@@ -41,7 +42,7 @@ static void edit_file(const struct passwd *pas, const char *file)
 	}
 
 	BB_EXECLP(ptr, ptr, file, NULL);
-	bb_perror_msg_and_die("exec %s", ptr);
+	bb_perror_msg_and_die("can't execute '%s'", ptr);
 }
 
 static int open_as_user(const struct passwd *pas, const char *file)
diff --git a/networking/ifupdown.c b/networking/ifupdown.c
index c7b560b..7706a84 100644
--- a/networking/ifupdown.c
+++ b/networking/ifupdown.c
@@ -106,6 +106,7 @@ enum {
 struct globals {
 	char **my_environ;
 	const char *startup_PATH;
+	char *shell;
 } FIX_ALIASING;
 #define G (*(struct globals*)&bb_common_bufsiz1)
 #define INIT_G() do { } while (0)
@@ -986,11 +987,10 @@ static int doit(char *str)
 
 		fflush_all();
 		child = vfork();
-		switch (child) {
-		case -1: /* failure */
+		if (child < 0) /* failure */
 			return 0;
-		case 0: /* child */
-			execle(DEFAULT_SHELL, DEFAULT_SHELL, "-c", str, (char *) NULL, G.my_environ);
+		if (child == 0) { /* child */
+			execle(G.shell, G.shell, "-c", str, (char *) NULL, G.my_environ);
 			_exit(127);
 		}
 		safe_waitpid(child, &status, 0);
@@ -1165,6 +1165,7 @@ int ifupdown_main(int argc UNUSED_PARAM, char **argv)
 	INIT_G();
 
 	G.startup_PATH = getenv("PATH");
+	G.shell = xstrdup(get_shell_name());
 
 	cmds = iface_down;
 	if (applet_name[2] == 'u') {
diff --git a/runit/svlogd.c b/runit/svlogd.c
index cfa20a7..b0ba21b 100644
--- a/runit/svlogd.c
+++ b/runit/svlogd.c
@@ -187,6 +187,7 @@ struct globals {
 	unsigned nearest_rotate;
 
 	void* (*memRchr)(const void *, int, size_t);
+	char *shell;
 
 	smallint exitasap;
 	smallint rotateasap;
@@ -382,6 +383,9 @@ static void processorstart(struct logdir *ld)
 	/* vfork'ed child trashes this byte, save... */
 	sv_ch = ld->fnsave[26];
 
+	if (!G.shell)
+		G.shell = xstrdup(get_shell_name());
+
 	while ((pid = vfork()) == -1)
 		pause2cannot("vfork for processor", ld->name);
 	if (!pid) {
@@ -416,8 +420,7 @@ static void processorstart(struct logdir *ld)
 		fd = xopen("newstate", O_WRONLY|O_NDELAY|O_TRUNC|O_CREAT);
 		xmove_fd(fd, 5);
 
-// getenv("SHELL")?
-		execl(DEFAULT_SHELL, DEFAULT_SHELL_SHORT_NAME, "-c", ld->processor, (char*) NULL);
+		execl(G.shell, G.shell, "-c", ld->processor, (char*) NULL);
 		bb_perror_msg_and_die(FATAL"can't %s processor %s", "run", ld->name);
 	}
 	ld->fnsave[26] = sv_ch; /* ...restore */
diff --git a/util-linux/script.c b/util-linux/script.c
index b9317fc..47efc45 100644
--- a/util-linux/script.c
+++ b/util-linux/script.c
@@ -65,10 +65,7 @@ int script_main(int argc UNUSED_PARAM, char **argv)
 	if (!(opt & OPT_q)) {
 		printf("Script started, file is %s\n", fname);
 	}
-	shell = getenv("SHELL");
-	if (shell == NULL) {
-		shell = DEFAULT_SHELL;
-	}
+	shell = get_shell_name();
 
 	pty = xgetpty(pty_line);
 
-- 
1.7.3.4



More information about the busybox-cvs mailing list