Are there names of environment variables that cannot be overwritten by the user/a call to setenv
? As I understand from POSIX1.2008, any process may edit the environment block, but must avoid overwriting such vars as LANG etc.
Shell – Protected environment variables
environment-variablesposixshell
Best Answer
The environment is a list of strings of the form
var=value
(by convention) that is passed as the 3rd argument to the execve() system call.That list is put somewhere on the stack of the process when it starts to execute the new command just like for the list of arguments (another list of strings passed as the second argument to
execve()
).In programs using the libc (most), an initialisation code called before the
main()
function is invoked, makes those environment strings available as theenviron
array.The
libc
also provides withputenv
andsetenv
functions that can modify (a copy of) that list that the program received. That maintained, modified copy will then be passed to the next command executed by the process or any of its children via theexecvp()
/execl()
/system()
/popen()
... functions of the libc (which themselves end up calling theexecve()
system call).Now while when you build up a list of strings that you pass manually to the
execve()
system call, you may pass strings likefoo
(without a=
character) or=bar
(with an empty variable name),setenv
won't let you do that (setenv("", "bar", 1)
is rejected).setenv("a=b", "c")
will also be rejected. So the strings that will be defined bysetenv
will always be of the formatx=y
wherex
may not be empty.That's about the only restriction (also applied by
putenv
). Well those being NUL terminated strings, of course the NUL character cannot appear in the variable name or value.setenv("*", "x", 1)
, orsetenv("\n\n", "", 1)
are all OK as far assetenv()
or the kernel are concerned. Now, whether you're going to be able to do anything useful with those is another matter.