6

Quoted from Wikipedia:

By default, when a process is created it inherits a duplicate environment of its parent process, except for explicit changes made by the parent when it creates the child. At API level, these changes must be done between fork and exec. Alternatively, from shells such as bash, you can change environment variables for a particular command invocation by indirectly invoking it via env or using the ENVIRONMENT_VARIABLE=VALUE notation.

I understand that "when a process is created it inherits a duplicate environment of its parent process". But I was wondering what the exception "explicit changes made by the parent when it creates the child" really means? I don't understand how the examples in API and shells are examples of the exception.

Caleb
  • 70,105
Tim
  • 101,790
  • See http://stackoverflow.com/questions/926185/about-fork-and-execve-system-call/931019#931019 for some of the explicit changes that can be made. – camh Aug 01 '11 at 04:05

2 Answers2

11

In the unix model, starting another program involves two primivites:

  • fork() creates an (almost) identical copy of the calling process. The new process is called the child process and the original process is called the parent process. The child process runs the same code as the original, has the same permissions, has the same environment, and receives a copy of the mutable data memory of the parent process. The most visible difference between the two processes is that they have different process IDs and different parent process IDs (the child's PPID is the parent's PID).
  • execve() replaces the code and data of the current process by code and data loaded from an executable file. This system call takes the new environment of the process as an argument.

Most high-level functions built around fork() and execve() pass the process's current environment to execve(). Thus, unless the process changes its own environment or calls execve() directly, the called program will inherit the calling program's environment.

Shells normally pass their environment to the programs they call. You can change the environment of a shell at any time by assigning a value to an environment variable (foo="some value"; you must call export foo if the variable isn't in the environment already), or remove a variable from the environment by unsetting it (unset foo). If you want to start an external program with different or additional environment variables, there is a shortcut syntax:

foo="some value" mycommand

is roughly equivalent to

(foo="some value"; export foo; exec mycommand)

(where the parentheses restrict the scope of the setting of foo).

  • 1
    Thanks! (1) Can the environment be changed when/after calling execve()? Is it more difficult than doing before execve() and after fork()? (2) foo="some value" mycommand doesn't work. Is there supposed to be a; before mycommand? – Tim Aug 07 '11 at 00:52
3

The APIs refers to the exec family of C functions that are used to execute another process.

The typical sequence for one process to start another is first to fork, then in the child just created, call one of the exec functions.

In between the fork and the exec, in the child process, the environment can be changed before the target executable is started.

The execle and execvpe also allow the calling process to pass in the target environment directly.

If execle and execvpe are not used, and the environment is not modified between the calls to fork and exec in the child, the normal rule applies.

The shell examples are meant to show you how you can change the environment for a child of your shell. If the shell didn't use some of the above "tricks", it could not let you do that - all the child processes would get an exact copy of your current shell's environment.

Mat
  • 52,586