Some of the variables discussed above are used by commands you may run-as opposed to the shell itself-so that they can determine certain aspects of your environment. The majority, however, are not even known outside the shell.
This dichotomy begs an important question: which shell "things" are known outside the shell, and which are only internal? This question is at the heart of many misunderstandings about the shell and shell programming. Before we answer, we'll ask it again in a more precise way: which shell "things" are known to subprocesses? Remember that whenever you enter a command, you are telling the shell to run that command in a subprocess; furthermore, some complex programs may start their own subprocesses.
Now for the answer, which (like many UNIX concepts) is unfortunately not as simple as you might like. A few things are known to subprocesses, but the reverse is not true: subprocesses can never make these things known to the processes that created them.
Which things are known depends on whether the subprocess in question is a Korn shell program (see Chapter 4) or interactive shell. If the subprocess is a Korn shell program, then it's possible to propagate every type of thing we've seen in this chapter-aliases, options, and variables-plus a few we'll see later.
By default, only one kind of thing is known to all kinds of subprocesses: a special class of shell variables called environment variables. Some of the built-in variables we have seen are actually environment variables: HISTFILE, HOME, LOGNAME, MAIL, MAILPATH, PATH, PWD, SHELL, and TERM.
It should be clear why these and other variables need to be known by subprocesses. We have already seen the most obvious example: text editors like vi and emacs need to know what kind of terminal you are using; TERM is their way of determining this. As another example, most UNIX mail programs allow you to edit a message with your favorite text editor. How does mail know which editor to use? The value of EDITOR (or sometimes VISUAL).
You can also define variables to be in the environment of a particular subprocess (command) only, by preceding the command with the variable assignment, like this:
You can put as many assignments before the command as you want.  For example, assume that you're using the emacs editor. You are having problems getting it to work with your terminal, so you're experimenting with different values of TERM. You can do this most easily by entering commands that look like:
 There is an obscure option, keyword, that (if turned on) lets you put this type of environment variable definition anywhere on the command line, not just at the beginning. Future releases, however, won't support this option.
TERM=trythisone emacs filename
emacs will have trythisone defined as its value of TERM, yet the environment variable in your shell will keep whatever value (if any) it had before. This syntax is not very widely used, so we won't see it very often throughout the remainder of this book.
Nevertheless, environment variables are important. Most .profile files include definitions of environment variables; the sample built-in .profile earlier in this chapter contained two such definitions:
EDITOR=/usr/local/bin/emacs SHELL=/bin/ksh export EDITOR
For some reason, the Korn shell doesn't make EDITOR an environment variable by default. This means, among other things, that mail will not know which editor to use when you want to edit a message.  Therefore you would have to export it yourself by using the above export command in your .profile.
The second line in the above code is meant for systems that do not have the Korn shell installed as the default shell, i.e., as /bin/sh. Some programs run shells as subprocesses within themselves (e.g., many mail programs and the emacs editor's shell mode); by convention they use the SHELL variable to determine which shell to use.
Although environment variables will always be known to subprocesses, the shell must be explicitly told which other variables, options, aliases, etc., are to be communicated to subprocesses. The way to do this is to put all such definitions in a special file called the environment file instead of your .profile.
Decide which definitions in your .profile you want to propagate to subprocesses. Remove them from .profile and put them in a file you will designate as your environment file.
Put a line in your .profile that tells the shell where your environment file is:
For the changes to take effect, type either . .profile or login.  In either case, your environment file will be run when the shell encounters the ENV= statement.
 The latter assumes that the Korn shell is defined as your login shell. If it isn't, you must do the former - or better yet, have your system administrator install it as your login shell!
The idea of the environment file comes from the C shell's .cshrc file; thus, many Korn shell users who came from the C shell world call their environment files .kshrc. (The rc suffix for initialization files is practically universal throughout the UNIX world. According to the folklore, it stands for "run commands" and has origins in old DEC operating systems.)
As a general rule, you should put as few definitions as possible in .profile and as many as possible in your environment file. Because definitions add to rather than take away from an environment, there is little chance that they will cause something in a subprocess not to work properly. (An exception might be name clashes if you go overboard with aliases.)
The only things that really need to be in .profile are commands that aren't definitions but actually run or produce output when you log in. Option and alias definitions should go into the environment file. In fact, there are many Korn shell users who have tiny .profile files, e.g.:
stty stop ^S intr ^C erase ^? date from export ENV=~/.kshrc
(The from command, in some versions of UNIX, checks if you have any mail and prints a list of message headers if you do.) Although this is a small .profile, this user's environment file could be huge.