aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRon Yorston <rmy@pobox.com>2022-02-12 12:59:04 +0000
committerRon Yorston <rmy@pobox.com>2022-02-12 12:59:04 +0000
commitc5270ab0c1bfe1f79bc57650da1091cd7358c689 (patch)
tree45bce329c790b92ce22f8be9beeb1b547c698426
parente6238530e486d3c4bfe5cab7df5545869ab139ad (diff)
downloadbusybox-w32-c5270ab0c1bfe1f79bc57650da1091cd7358c689.tar.gz
busybox-w32-c5270ab0c1bfe1f79bc57650da1091cd7358c689.tar.bz2
busybox-w32-c5270ab0c1bfe1f79bc57650da1091cd7358c689.zip
ash: workaround for UCRT bug
There seems to be a bug in UCRT such that if a process has been started by passing a non-NULL environment block to CreateProcess() any subsequent call to spawnve() with a non-NULL environment pointer results in a crash. Commit 5b48ca53b (win32: pass NULL to spawnve, not environ) fixed the problem in busybox-w32 for those cases where a NULL environment pointer was sufficient. It didn't handle the case where the shell passes a modified environment to its child. All calls to spawnve() in the shell occur in a process which will terminate whether or not the call succeeds. It therefore doesn't matter if we mess with the environment of this process to allow spawnve() to be passed a NULL environment pointer. Do this for UCRT builds only. (GitHub issue #234)
-rw-r--r--shell/ash.c12
1 files changed, 12 insertions, 0 deletions
diff --git a/shell/ash.c b/shell/ash.c
index 46c4f1675..c9122b291 100644
--- a/shell/ash.c
+++ b/shell/ash.c
@@ -8899,9 +8899,13 @@ tryexec(IF_FEATURE_SH_STANDALONE(int applet_no,) const char *cmd, char **argv, c
8899# else 8899# else
8900 if (APPLET_IS_NOEXEC(applet_no)) { 8900 if (APPLET_IS_NOEXEC(applet_no)) {
8901# endif 8901# endif
8902#if ENABLE_PLATFORM_MINGW32 && !defined(_UCRT)
8903 /* If building for UCRT move this up into shellexec() to
8904 * work around a bug. */
8902 clearenv(); 8905 clearenv();
8903 while (*envp) 8906 while (*envp)
8904 putenv(*envp++); 8907 putenv(*envp++);
8908#endif
8905 popredir(/*drop:*/ 1); 8909 popredir(/*drop:*/ 1);
8906 run_noexec_applet_and_exit(applet_no, cmd, argv); 8910 run_noexec_applet_and_exit(applet_no, cmd, argv);
8907 } 8911 }
@@ -8971,6 +8975,14 @@ static void shellexec(char *prog, char **argv, const char *path, int idx)
8971 int applet_no = -1; /* used only by FEATURE_SH_STANDALONE */ 8975 int applet_no = -1; /* used only by FEATURE_SH_STANDALONE */
8972 8976
8973 envp = listvars(VEXPORT, VUNSET, /*strlist:*/ NULL, /*end:*/ NULL); 8977 envp = listvars(VEXPORT, VUNSET, /*strlist:*/ NULL, /*end:*/ NULL);
8978#if ENABLE_PLATFORM_MINGW32 && defined(_UCRT)
8979 /* Avoid UCRT bug by updating parent's environment and passing a
8980 * NULL environment pointer to execve(). */
8981 clearenv();
8982 while (*envp)
8983 putenv(*envp++);
8984 envp = NULL;
8985#endif
8974#if !ENABLE_PLATFORM_MINGW32 8986#if !ENABLE_PLATFORM_MINGW32
8975 if (strchr(prog, '/') != NULL 8987 if (strchr(prog, '/') != NULL
8976#else 8988#else