diff --git a/src/uu/env/src/env.rs b/src/uu/env/src/env.rs index aec97fc24..2bf5ed7d1 100644 --- a/src/uu/env/src/env.rs +++ b/src/uu/env/src/env.rs @@ -7,7 +7,7 @@ /* last synced with: env (GNU coreutils) 8.13 */ -// spell-checker:ignore (ToDO) chdir execvp progname subcommand subcommands unsets +// spell-checker:ignore (ToDO) chdir execvp progname subcommand subcommands unsets setenv putenv #[macro_use] extern crate clap; @@ -256,7 +256,32 @@ fn run_env(args: impl uucore::Args) -> UResult<()> { // set specified env vars for &(name, val) in &opts.sets { - // FIXME: set_var() panics if name is an empty string + /* + * set_var panics if name is an empty string + * set_var internally calls setenv (on unix at least), while GNU env calls putenv instead. + * + * putenv returns successfully if provided with something like "=a" and modifies the environ + * variable to contain "=a" inside it, effectively modifying the process' current environment + * to contain a malformed string in it. Using GNU's implementation, the command `env =a` + * prints out the malformed string and even invokes the child process with that environment. + * This can be seen by using `env -i =a env` or `env -i =a cat /proc/self/environ` + * + * POSIX.1-2017 doesn't seem to mention what to do if the string is malformed (at least + * not in "Chapter 8, Environment Variables" or in the definition for environ and various + * exec*'s or in the description of env in the "Shell & Utilities" volume). + * + * It also doesn't specify any checks for putenv before modifying the environ variable, which + * is likely why glibc doesn't do so. However, setenv's first argument cannot point to + * an empty string or a string containing '='. + * + * There is no benefit in replicating GNU's env behavior, since it will only modify the + * environment in weird ways + */ + + if name.is_empty() { + show_warning!("no name specified for value {}", val.quote()); + continue; + } env::set_var(name, val); }