I have a parent process running as 'root' user. After fork(), execl() and setuid()/setgid(), the child process is started as another OS user (say user1).

Printing the environment shows that this is same as the root environment (as if logging in as root) and not as if logging in as user1. Why?

Is there a way to read the environment of user1 in the child process?

  • You want running environment or just environment ? – Rahul Patil Apr 2 '13 at 9:11

Each process has its own environment, copied from the parent. If the parent is a shell, there's a concept of exportable variables which needs to be considered, but this does not apply when you are dealing with exec() etc directly. The LOGNAME variable is typically set by a login shell, you're just seeing a leftover value that was not reset. So, you are seeing the child environment. On some systems you cannot easily access the parent (or other process) environment, on Linux you can do this easily (subject to permissions) via /proc)

You can probably reproduce the effect you are seeing by trying both su and su -, the latter will initialize a shell login environment which will (almost certainly) reset LOGNAME amongst other things, the former will leave it untouched.

Using the env command is one way of getting a clean environment when starting a new process from a command line, you should check the execle() documentation on your system to see how to do something similar.

| improve this answer | |

You can simply check user env using :

su -l user_name  -c "run_programm && env"

Or you can check env of child process by using it's pid ,

suppose your child process pid is 24112 , then just check env using :

cat /proc/24112/environ
| improve this answer | |
  • I needed programatically (Unix/C) and common for all the Unix platforms. – Balu T Apr 3 '13 at 8:38
  • @BaluT, you can use execl("su", "-l", "user_name", "-c", "program"); in your code. – Alexis Wilke Jul 29 '15 at 7:03

Some bits of information:

  • You can use execle or execve to provide enviroment variables to the child. You can use this both to suppress environment variables from the parent process which are no longer suitable for the child, and to provide additional variables to the child.
  • You can start a “login shell” for the child, e.g. using bash -l. This will populate the enviroment as for a child. For many shells (including bash), prepending a hyphen to the name of the binary, i.e. passing -bash as argv[0], has the same effect. A primary effect of this distinction is that a login shell will execute the /etc/profile and/or other profile shell scripts, which in turn set a large number of environment variables.
  • For services which use PAM for authentication and session initialization, the pam_env module will take care of properly initializing the environment. You can have a look at that and its configuration, either to use it or to mimic its behaviour.
| improve this answer | |

Each process has a set of environment variables (that can be set in a shell by export SOMEVAR=value and so). They are inherited as-is by child processes. If you want to reset them, use extern char **environ; to get at the passed environment (see environ(7)), and then use execle(3) or execve(3) passing a new environment array with copied variable values. Some guidance on what and how do do it is given by David Wheeler in his "Secure Unix/Linux programming HOWTO"

| improve this answer | |
  • When the parent process is running as root,the environ is set to root environment. then when the parent process forks, the child process has the same environ (as was used by root) even though the effective uid/gid are changed for the child process. So my Question is how to access the environ of child process running as different uid/gid ? – Balu T Apr 3 '13 at 8:40

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.