Environment Variables
The OS stores environment variables for every process. Like variables in a program, each has a name and a value. By convention, names are all upper case, and values are always strings. Type set at the command prompt to get a listing:
$ set
BASH=/usr/bin/bash
BASH_VERSION='2.05b.0(1)-release'
COLUMNS=120
HISTFILE=/home/.bash_history
HISTFILESIZE=500
HISTSIZE=500
HOME=/home/rweasley
HOSTNAME=hogwarts
HOSTTYPE=i686
LINES=60
NUMBER_OF_PROCESSORS=1
OSTYPE=cygwin
PATH='/usr/local/bin:/usr/bin:/bin:/Python24:/home/rweasley/bin'
PWD=/home/rweasley
SHELL=/bin/bash
UID=1003
USER=rweasley
You can get a variable's value by putting "$" in front of its name, so ls $HOME is the same as ls /home/rweasley (if you're Ron Weasley). Use the echo command to print out a variable's value:
$ echo $HOME
/cygdrive/c/home/rweasley
If a variable hasn't been defined, its value is the empty string (rather than an error).
Setting Environment Variables
Different shells have different syntaxes for setting environment variables. For Bash, use this:
$ VILLAIN="Lord Voldemort"
Notice that values with spaces in them have to be quoted.
Setting an environment variable only affects that program (i.e., that shell). To see this, set a variable, then run a new shell, and echo the variable's value:
$ VILLAIN="Lord Voldemort"
$ bash
$ echo
$VILLAIN
$ exit
If you want programs run from that shell to inherit the value, you must export it:
$ VILLAIN="Lord Voldemort"
$ export VILLAIN
$ bash
$ echo $VILLAIN
Lord Voldemort
$ exit
In fact, you can perform both operations in a single step:
$ export VILLAIN="Lord Voldemort"
$ bash
$ echo $VILLAIN
Lord Voldemort
$ exit
Configuration
To set a variable's value automatically when you log in, edit ~/.bashrc ("~" is a shortcut meaning “your home directory”):
# Add personal tools directory to PATH.
PATH=$HOME/bin:$PATH
# Personal settings.
export EDITOR=/local/bin/emacs
export PRINTER=gryffindor-laserwriter
# Change default behavior of commands.
alias ls="ls -F"
Note: .bashrc files can become very complex…
Many applications look for personal configuration files in the user's home directory. By convention, their names begin with “.” so that a normal ls won't show them. Once upon a time, the “rc” at the end meant “run commands”.
How the Shell Finds Programs
The PATH environment variables defines the shell's search path. When you run a command like broom, the shell:
- Splits $PATH into components to get a list of directories (Unix uses “:” as a separator, while Windows uses “;”)
- Looks for the program in each directory in left-to-right order
- Runs the first one that it finds
Example:
- Suppose PATH is /home/rweasley/bin:/usr/local/bin:/usr/bin:/bin:/Python24
- Both /usr/local/bin/broom and /home/rweasley/bin/broom exist
- /home/rweasley/bin/broom will be run when you type broom at the command prompt
- we can run the other one by specifying the path, instead of just the command name
Common Search Path Entries
Directories /bin and /usr/bin contain core tools like ls. The word “bin” comes from “binary”, which is geekspeak for “a compiled program”.
Directory /usr/local/bin contains optional (but common) tools, like the gcc C compiler.
Directory $HOME/bin contains tools you have built for yourself. Remember, $HOME is your home directory.
It is also common to include . (the current working directory) in your path. This allows you to run a program in the current directory using whatever, instead of ./whatever.
Cygwin on Windows
Cygwin does things a little differently - it uses the notation /cygdrive/c/somewhere instead of Windows' C:/somewhere. Because the colon in C:/somewhere would clash with the colons in the PATH variable. By default, Cygwin treats C:/cygwin as the root of its file system, so /home/rweasley is a synonym for C:/cygwin/home/rweasley. Yes, it can be confusing, but then again, it is trying to make one operating system look like another.