summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarc Espie <espie@cvs.openbsd.org>2012-09-05 22:15:30 +0000
committerMarc Espie <espie@cvs.openbsd.org>2012-09-05 22:15:30 +0000
commit00e04ffedcb9bce637bf0eb4ef36bcb0a696c425 (patch)
tree2845510faa929f3b63fda78141d9b4437cfa3baf
parent25c15b00c4acace4866d87ae94d4b2610ebbca86 (diff)
sh -c should not munge argv[].
This fixes ps -ww output. joint work by millert@ and me@. okay otto@, deraadt@ "feel free to commit my version" millert@
-rw-r--r--bin/ksh/main.c22
1 files changed, 19 insertions, 3 deletions
diff --git a/bin/ksh/main.c b/bin/ksh/main.c
index 0718a637590..61dc56799dd 100644
--- a/bin/ksh/main.c
+++ b/bin/ksh/main.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: main.c,v 1.47 2011/09/07 11:33:25 otto Exp $ */
+/* $OpenBSD: main.c,v 1.48 2012/09/05 22:15:29 espie Exp $ */
/*
* startup, main loop, environments and error handling
@@ -67,6 +67,23 @@ char username[_PW_NAME_LEN + 1];
#define version_param (initcoms[2])
+/* modifying argv will modify ps output, so sh -c needs to copy part of it
+ * to be able to parse further options
+ */
+static char **
+copy_argv(int argc, char *argv[])
+{
+ int i;
+ char **nargv;
+
+ nargv = alloc(sizeof(char *) * (argc + 1), &aperm);
+ nargv[0] = (char *) kshname;
+ for (i = 1; i < argc; i++)
+ nargv[i] = argv[i];
+ nargv[i] = NULL;
+ return nargv;
+}
+
int
main(int argc, char *argv[])
{
@@ -314,9 +331,8 @@ main(int argc, char *argv[])
#endif
l = e->loc;
- l->argv = &argv[argi - 1];
l->argc = argc - argi;
- l->argv[0] = (char *) kshname;
+ l->argv = copy_argv(l->argc, &argv[argi - 1]);
getopts_reset(1);
/* Disable during .profile/ENV reading */