sh — Invoke a shell

[r]sh [-abCefhiKkLmnprtuvx] [-o option] [cmd_file [argument...]]
[r]sh -c cmdstring [-abCefhiKkLmnprtuvx] [-o option] [cmd_name [argument...]]
[r]sh -s [-abCefhikLmnprtuvx] [-o option] [argument...]

Purpose

sh contains the following subsections:
  • Options and invocation
  • Command syntax
  • Command execution
  • Quoting
  • Directory substitution
  • Parameter substitution
  • Arithmetic substitution
  • Command substitution
  • File descriptors and redirection
  • File name generation
  • Variables
  • Shell execution environments
  • Built-in commands

Subsections dealing with substitution and interpretation of input appear in the order in which the shell performs those substitutions and interpretations.

Much of what the shell can do is provided through such built-in commands as cd and alias.

Invocation Options

The OpenExtensions shell, based on the KornShell, is upward-compatible with the Bourne shell.

Normally you invoke the shell with OPENVM SHELL. You can also invoke the shell by typing an explicit sh command. Some people find it useful to copy the sh file into a file named rsh. If you invoke the shell under the name rsh, the shell operates in restricted mode. This mode is described in connection with –r.

If you invoke the shell with a name that begins with the character, it is a login shell. (You can also get a login shell if you invoke the shell with the –L option.) A login shell begins by running the file /etc/profile. It then runs $HOME/.profile using the . command (see dot). If $HOME is not set, the shell searches the working directory for:
.profile
and runs this file with the . command if it exists. You do not get an error message if any of these files cannot be found.

You can use these profile files to customize your session with sh. For example, your profile files can set options, create aliases, or define functions and variables.

If there is at least one argument on the sh command line, sh takes the first argument as the name of a shell script to run. (The exception to this is when –s is used.) Any additional arguments are assigned to the positional parameters; usually, these serve as arguments to the shell script. See Parameter Substitution for information about positional parameters, and see set for information about changing these parameters.

If sh finds the ENV environment variable set when it begins running (after profile processing), sh runs the file named by the expansion of the value of this variable (see Variables).

Command Options

The shell accepts the following options on the command line:
–c cmdstring
Runs cmdstring as if it were an input line to the shell and then exits. This is used by programs (for example, editors) that call the shell for a single command. sh assigns arguments after cmdstring to the positional parameters. If you specify cmd_name, special parameter 0 is set to this string for use when running the commands in cmdstring.
–i
Invokes an interactive shell, as opposed to running a script. With –i, the shell catches and ignores interrupts. Without –i, an interrupt ends the shell. For shells that read from the terminal, –i is the default.
–K
Specifies KornShell-compatible behavior where the POSIX.2 behavior is different from the behavior specified by the KornShell. Without -K, the shell defaults to POSIX.2 behavior.
–L
Makes the shell a login shell, as described earlier.
–r
Invokes a restricted shell. (As noted earlier, you can also invoke a restricted shell by using the name rsh). In a restricted shell, you cannot do the following: use the cd command; change the values of the variables ENV, PATH, or SHELL; use > or >> to redirect output; or specify command names containing /. These restrictions do not apply during execution of your profile files.
–s
Reads commands from standard input and assigns all arguments to the positional parameters. Normally, if there is at least one argument to the shell, the first such argument is the name of a file to run.

If you do not give either the –c or –s option, but you do specify cmd_file, the shell takes it as the name of a file that contains commands to be run. Special parameter 0 is set to this name.

In addition to these options, you can use any valid option to the set command (including –o option) as a command-line option to sh. See set for details.

Command Syntax

The shell implements a sophisticated programming language that gives you complete control over the execution and combination of individual commands. When the shell scans its input, it always treats the following characters specially:
*   ;   &   (   )   <   >   |   '   \   "
space   tab   newline
If you want to use any of these characters inside an actual argument, you must quote the argument (so that the shell doesn't use the special meanings of the characters). See Quoting for more information.

A simple command is a list of arguments separated by characters in the IFS environment variable (the default value of IFS has blank, tabs, and newlines).

When a word is preceded by an unescaped pound sign (#), the remainder of the line is treated as a comment, and the shell discards input up to but not including the next newline. When a command starts with a defined alias, sh replaces the alias with its definition (see alias).

A reserved-word command starts with a reserved word (for example, if, while, or for). Reserved-word commands provide flow of control operations for the shell. These are described in Reserved-Word Commands.

A command can be any of the following:
command:
simple command
reserved-word command
(command)
command | command
command && command
command || command
command & command
command &
command |&
command ; command
command ;
command<newline>
The following is the order of precedence of the preceding operators. The highest priority operators are listed first, and operators on the same line have equal priority.
()
|
&&     ||
&      |&       ;      <newline>
The meaning of these operations is as follows:
(command)
Runs command in a subshell. The current shell invokes a second shell, and this second shell actually runs command. In this way, command runs in a completely separate execution environment; it can change working directories, change variables, open files, and so on without affecting the first shell. The subshell's environment begins as a copy of the current environment, so the value of the ENV environment variable is not run when a subshell starts.
|
Creates a pipe between the two commands that the | operator connects. The standard output of the first command becomes the standard input of the second command. A series of commands connected by pipes is called a pipeline. The exit status is that of the last command in the pipeline.
&&
Is the logical AND operator. The shell runs the second command if and only if the first command returns a true (zero) exit status.
||
This is the logical OR operator. The shell runs the second command if and only if the first command returns a false (nonzero) exit status.
&
Runs the command that precedes it asynchronously. The shell just starts the command running and then immediately goes on take new input, before the command finishes execution. On systems where asynchronous execution is not possible, this operation is effectively equivalent to ;.
|&
Runs the command that precedes it as a co-process. The command runs asynchronously, as with the & operator, but the command's standard input and standard output are connected to the shell by pipes. The shell sends input to command 's standard input with the print –p command, and reads from command's standard output with the read –p command. The command should not buffer its output. Because of this and other limitations, co-processes should be designed to be used as co-processes. On systems where asynchronous execution is not possible, co-processes are not supported.
;
Is the sequential execution operator. The second command is run only after the first command has completed.
newline
The unescaped newline is equivalent to the ; operator.

Reserved-Word Commands

The shell contains a rich set of reserved-word commands, which provide flow of control and let you create compound commands. In the following list, a command can also be a sequence of commands separated by newlines. Square brackets ([ ]) indicate optional portions of commands, and are never part of the command syntax.
! command
The exclamation point is the logical NOT operator. When command returns false (nonzero), ! returns true (zero). When command returns true (zero), ! returns false (nonzero).
{ command;}
Enclosing a command in braces is similar to the (command) construct, except that the shell runs the command in the same environment rather than under a subshell. { and } are simply reserved words to the shell. To make it possible for the shell to recognize these symbols, you must put a blank or newline after the {, and a semicolon or newline before the }.
case word in | [(][pattern[|pattern] ... )command ;;] ... | [(][pattern[| pattern] ... )command ;; ] ... | esac
The case statement is similar to the switch statement of the C programming language or the case statement of Pascal. If the given word matches any one of the patterns separated by or bar (|) characters, sh runs the corresponding command. The patterns should follow the rules given in File Name Generation, except that the period (.) and slash (/) are not treated specially. Patterns are matched in the order they are given, so more inclusive patterns should be mentioned later. You must use the double semicolon (;;) to delimit command and introduce the next pattern.
for variable [in word ...] | do command | done
The for statement sets variable to each word argument in turn, and runs the set of commands once for each setting of variable. If you omit the in word part, sh sets variable to each positional parameter. You can divert the flow of control within the loop with the break or continue statements.
function variable { | command | } | variable() { | command | }
Any one of these forms defines a function named variable, the body of which consists of the sequence of commands. You invoke a function just like any other command; when you actually call the function, sh saves the current positional parameters. The function's command-line arguments then replaces these parameters until the function finishes. sh also saves the current ERR and EXIT traps and any flags manipulated with the set command; these are restored when the function finishes. The function ends either by falling off the end of the code of the function body, or by reaching a return statement. If the function uses typeset to declare any variables in the function body, the variables are local to the function.
if command | then command | [elif command | then command] ... | [else command] | fi
In the if statement, if the first (leftmost) command succeeds (returns a zero exit status), sh runs the command following then. Otherwise, sh runs the command (if any) following the elif (which is short for else if); if that succeeds, sh runs the command following the next then. If neither case succeeds, sh runs the command following the else (if any).
select variable [in word ...] | do commands | done
The select statement can handle menulike interactions with the user. Its syntax is like the for statement. Each word is printed on the standard error file, one per line, with an accompanying number. If you omit the “in word ...” part, sh uses the positional parameters. sh then displays the value of the variable PS3 to prompt the user to enter a numerical reply. If the reply is an empty line, sh displays the menu again; otherwise, sh assigns the input line to the variable REPLY, sets variable to the word selected, and then runs the commands. sh does this over and over until the loop is ended by an interrupt, an end-of-file, or an explicit break statement in the commands.
until command1 | do command2 | done
The until statement runs command1 and tests its exit status for success (zero) or failure (nonzero). If command1 succeeds, the loop ends; otherwise, sh runs command2 and then goes back to run and test command1 again. break and continue commands in the commands can affect the operation of the loop.
while command1 | do command2 | done
The while statement works similarly to the until statement. However, the loop ends whenever command1 is unsuccessful (nonzero exit status).

Shell reserved words are recognized only when they are the unquoted first token of a command. This lets you pass these reserved words as arguments to commands run from the shell. The full list of reserved words is:

Command Execution

Before running a simple command, the shell processes the command line, performing expansion, assignments, and redirection.

First, sh examines the command line and divides it into a series of tokens, which are either operators or words. An operator is either a control operator (described in Command Syntax) or a redirection operator (described in File Descriptors and Redirection). A word is any token that is not an operator.

Next, the shell expands words in the following order:

  1. sh performs directory substitution (see Directory Substitution).
  2. sh performs parameter substitution, command substitution, or arithmetic substitution, as appropriate, in the order that the words appear on the command line, expanding each word to a field (see the appropriate sections).
  3. sh scans each field produced in step 2 for unquoted characters from the IFS environment variable and further subdivides this field into one or more new fields.
  4. sh expands any aliases to their definitions (see alias — Display or create a command alias).
  5. sh performs path name expansion on each unquoted field from step 3 (see File Name Generation).
  6. sh removes all quote mechanisms (\, ', and ") that were present in the original word unless they have themselves been quoted (see Quoting).

The shell considers the first field of the expanded result to be a command.

The expanded simple command can contain variable assignments and redirections. Variable assignments affect the current execution environment. After expansion, the shell handles all redirection constructs, and the command, if one was found, it performs the redirection in a subshell environment (see Shell Execution Environments).

When a simple command contains a command name, variable assignments in the command affect only the execution of that command.

After the shell has expanded all appropriate arguments in a simple command, but before it performs file name generation, it examines the command name (if the command has one). sh checks the names against currently defined aliases (see alias) and functions (see function under Command Syntax), and finally against the set of built-in commands: commands that the shell can run directly without searching for program files. Built-in commands are described in Built-In Commands.

If the command name is not a function or a built-in command, the shell looks for a program file or script file that contains an executable version of that command. The OpenExtensions shell uses the following procedure to locate the program file:
  • If the command name typed to the shell has slash (/) characters in its name, the command is taken to be a full path name (absolute or relative). The shell tries to execute the contents of that file.
  • Otherwise, the shell performs a path search. To do this, the shell obtains the value of the PATH environment variable. The value should be a list of directory names. sh searches under each directory for a file, the name of which matches the command name. sh runs the first matching file found.

Command names can be marked as tracked aliases. The first time you run a command with a tracked alias, the shell does a normal PATH search. If the search is successful, the shell remembers the file that it finds. The next time you run a command with the same name, sh immediately runs the file found on the last PATH search; there is no new search. This speeds up the time that it takes the shell to find the appropriate file.

The set –h command tells the shell that all commands should be treated as tracked aliases. See alias and set for more information.

Quoting

To let you override the special meaning of certain words or special characters, the shell provides several quoting mechanisms. In general, you can turn off the special meaning of any character by putting a backslash (\) in front of the character. This is called escaping the character.

For example, you can tell the shell to disregard the special meaning of the newline character by putting a backslash at the very end of a line. The shell ignores the escaped newline, and joins the next line of input to the end of the current line. In this way, you can enter long lines in a convenient and readable fashion.

Escaping characters by putting a backslash in front of them is the most direct way of telling the shell to disregard special meanings. However, it can be awkward and confusing if you have several characters to escape.

As an alternative, you can put arguments in various types of quotes. Different quotation mark characters have different strengths. The single quotation mark characters are the strongest. When you enclose a command-line argument in single quotation mark characters, the shell disregards the special meanings of everything inside the single quotation marks. For example:
 echo '*'
displays just the * character.
Double quotation mark characters are weaker. Inside double quotation marks, the shell performs command substitutions of the form:
$(command)
or:
command
(See Command Substitution.) The shell does not perform such substitutions when they appear inside single quotation marks. In addition, the shell performs parameter substitutions of the form:
$parameter
when they are inside double quotation marks but not when they're inside single quotation marks (see Parameter Substitution). You can use the backslash to escape another character when they appear inside double quotation marks, but inside single quotation marks the shell ignores this special meaning.

The shell treats internal field separator characters (that is, characters in the value of the IFS variable) literally inside quoted arguments, whether they're quoted with double quotation marks or single quotation marks. This means that a quoted argument is considered a single entity, even if it contains IFS characters.

Quoting can override the special meanings of reserved words and aliases. For example, in:
"time" program
the quotes around time tell the shell not to interpret time as a shell reserved word. Instead, sh does a normal command search for a command named time.
You must always quote the following characters if you want sh to interpret them literally:
|   &   ;   <   >   (   )   $    '   "   ˋ   \
<space>  <tab>  <newline>
The following characters need to be quoted in certain contexts if they are to be interpreted literally:
*   ?   [   #   %   =   ~

Directory Substitution

When a word begins with an unquoted tilde ( ~), sh tries to perform directory substitution on the word. sh obtains all characters from the tilde ( ~) to the first slash (/) and uses this as a user name. sh looks for this name in the user profile, the file that contains information on all the system's users. If sh finds a matching name, it replaces ~name with the name of the user's home directory, as given in the matching POSIX user database.

For example, if you specify a file name as:
 ~jsmith/file
sh would look up jsmith's home
directory and put that directory name in place
of the  ~jsmith
construct.
If you specify a ~ without an accompanying name, sh replaces the ~ with the current value of your HOME variable (see Environment Variables). For example:
echo  ~
displays the name of your home directory. Similarly, sh replaces
the construct  ~+ with the value of the PWD variable (the name of the
your working directory), and replaces the tilde hyphen ( ~–) with the
value of OLDPWD (the name of your previous working directory). In variable
assignments, tilde expansion is also performed after colons (:).

Parameter Substitution

The shell uses three types of parameters: positional parameters, special parameters, and variables. A positional parameter is represented with either a single digit (except 0) or one or more digits in curly braces. For example, 7 and {15} are both valid representations of positional parameters. Positional parameters are assigned values from the command line when you invoke sh.

A special parameter is represented with one of the following characters:
*    @    #    ?    !    -    $     0
The values to which special parameters expand are listed in the following paragraphs.

Variables are named parameters. For details on naming and declaring variables, see Variables.

The simplest way to use a parameter in a command line is to enter a dollar sign ($) followed by the name of the parameter. For example, if you enter the command:
echo $x
sh replaces $x with the value of the parameter x and then displays the results (because echo displays its arguments). Other ways to expand parameters are shown in the following paragraphs.
The following parameters are built in to the shell:
$1, $2, ... $9
Expands to the d positional parameter (where d is the single digit following the $). If there is no such parameter, $d expands to a null string.
$0
Expands to the name of the shell, the shell script, or a value assigned when you invoked the shell.
$#
Expands to the number of positional parameters.
$@
Expands to the complete list of positional parameters. If $@ is quoted, the result is separate arguments, each quoted. This means that:
"$@"
is equivalent to:
"$1" "$2" ...
$*
Expands to the complete list of positional parameters. If $* is quoted, the result is concatenated into a single argument, with parameters separated by the first character of the value of IFS (Variables). For example, if the first character of IFS is a blank, then:
"$*"
is equivalent to:
"$1 $2 ..."
$–
Expands to all options that are in effect from previous calls to the set command and from options on the sh command line.
$?
Expands to the exit status of the last command run.
$$
Expands to the current process number of the original parent shell.
$!
Expands to the process number of the last asynchronous command.

These constructs are called parameters of the shell. They include the positional parameters, but are not restricted to the positional parameters.

We have already mentioned that you can expand a parameter by putting a $ in front of the parameter name. More sophisticated ways to expand parameters are:
${parameter}
Expands any parameter.
${number}
Expands to the positional parameter with the given number. (Remember that if you just enter $d to refer to the dth positional parameter, d can only be a single digit; with brace brackets, number can be greater than 9.) Since braces mark the beginning and end of the name, you can have a letter or digit immediately following the expression.
${variable[arithmetic expression]}
Expands to the value of an element in an array named variable. The arithmetic expression gives the subscript of the array. (See Arithmetic Substitution.)
${variable[*]}
Expands to all the elements in the array variable, separated by the first character of the value of $IFS
${variable[@]}
When unquoted, is the same as ${variable[*]}. When quoted as ${variable[@]}, it expands to all the elements in the array variable, with each element quoted individually.
${#parameter}
Expands to the number of characters in the value of the given parameter.
${#*}, ${#@}
Expands to the number of positional parameters.
${#variable[*]}
Expands to the number of elements in the array named variable. Elements that do not have assigned values do not count. For example, if you only assign values to elements 0 and 4, the number of elements is 2. Elements 1 through 3 do not count.
${parameter:–word}
Expands to the value of parameter if it is defined and has a nonempty value; otherwise, it expands word. This means that you can use word as a default value if the parameter isn't defined.
${parameterword}
Is similar to the preceding construct, except that the parameter is expanded if defined, even if the value is empty.
${variable:=word}
Expands word with parameter expansion and assigns the result to variable, provided that variable is not defined or has an empty value. The result is the expansion of variable, whether or not word was expanded.
${variable=word}
Is similar to the preceding construct, except that the variable must be undefined (it cannot just be null) for word to be expanded.
${parameter:?word}
Expands to the value of parameter provided that it is defined and non-empty. If parameter isn't defined or is null, sh expands and displays word as a message. If word is empty, sh displays a default message. After a noninteractive shell has displayed a message, it ends.
${parameter?word}
Is similar to the preceding construct, except that sh displays word only if parameter is undefined.
${parameter:+word}
Expands to word, provided that parameter is defined and nonempty.
${parameter+word}
Expands to word, provided that parameter is defined.
${parameter#pattern}
Attempts to match pattern against the value of the specified parameter. The pattern is the same as a case pattern. sh searches for the shortest prefix of the value of parameter that matches pattern. If sh finds no match, the previous construct expands to the value of parameter; otherwise, the portion of the value that matched pattern is deleted from the expansion.
${parameter##pattern}
Is similar to the preceding construct, except that sh deletes the longest part that matches pattern if it finds such a match.
${parameter%pattern}
Searches for the shortest suffix of the value of parameter matching pattern and deletes the matching string from the expansion.
${parameter%%pattern}
Is similar to the preceding construct, except that sh deletes the longest part that matches pattern if it finds such a match.

Arithmetic Substitution

Arithmetic substitution is available with the syntax:
$((arithmetic expression))
or:
$[arithmetic expression]
This sequence is replaced with the value of arithmetic expression. Arithmetic expressions consist of expanded variables, numeric constants, and operators. Numeric constants have the form:
[base#]number
where the optional base is a decimal integer between 2 and 36 inclusive, and number is any nonnegative number in the given base. The default base is 10. Undefined variables evaluate to zero.
The operators are listed in decreasing order of precedence in Table 1. Operators sharing a heading have the same precedence. Evaluation within a precedence group is from left to right, except for the assignment operator, which evaluates from right to left.
Table 1. Shell Operators
Category Function
Unary Operators
  - Unary minus
  ! Logical negation
  + ~ Identity, bitwise negation
Multiplicative Operators
  * / % Multiplication, division, remainder
Additive Operators
  + - Addition, subtraction
Bitwise Shift Operators
  << >> Bitwise shift right, bitwise shift left
Relational Operators
  < > Less than, greater than
  <= >= Less than or equal, greater than or equal
  = = != Equal to, not equal to
Bitwise AND Operator
  & AND
Bitwise Exclusive OR Operator
  ^ Exclusive OR
Bitwise Inclusive OR Operator
  | Inclusive OR
Logical AND Operator
  && Logical AND
Logical OR Operator
  || Logical OR
Conditional Operator
  ? : If-else
Assignment Operator
  = *= /= %=
  += -= <<=
  >>= &= ^= |=
Assignment
Arithmetic expressions can be used without the enclosing $(( and )) in assignment to an integer variable (see typeset) as an argument to the following built-in commands: and when used as arguments in test numeric comparisons (–eq, –ge, –gt, –le, –lt, and -ne) (see test).

Command Substitution

In command substitution, sh uses the expansion of the standard output of one command in the command line for a second command. There are two syntaxes.

The first syntax (called backquoting) surrounds a command with grave accents ˋ, as in:
ls -l ˋcat listˋ
To process this command line, sh first runs the cat command and collects its standard output. The shell then breaks this output into arguments and puts the result into the command line of the ls command. The previous command therefore lists the attributes of all files, the names of which are contained in the file list.
This syntax is easy to type, but is not useful if you want to put one command substitution inside another (nesting command substitutions). A more useful syntax is:
$(command)
as in:
ed $(grep -f -l function $(find . -name '*.c'))
This command uses find to search the current directory and its subdirectories to find all files, the names of which end in .c. It then uses grep –f to search each such file for those that contain the string function. Finally, it calls ed to edit each such file.
There is a historical inconsistency in the backquoting syntax. A backslash (\) within a backquoted command is interpreted differently depending on its context. Backslashes are interpreted literally unless they precede a dollar sign ($), grave accent ( ˋ), or another backslash (\). In these cases, the leading backslash becomes an escape character to force the literal interpretation of the $, ˋ, or \. Consequently, the command:
echo '\$x'
issued at system level produces the output:
\$x
whereas the same command nested in a backquoted syntax:
echo ˋecho '\$x'ˋ
produces the output:
$x
We recommend the $(command) syntax for command substitutions.

sh performs command substitutions as if a new copy of the shell is invoked to run the command. This affects the behavior of $- (standing for the list of options passed to the shell). If a command substitution contains $-, the expansion of $- does not include the –i option, since the command is being run by a noninteractive shell.

File Descriptors and Redirection

The shell sometimes refers to files using file descriptors. A file descriptor is a number in the range 0 to 9. It may have any number of digits. For example, the file descriptors 001 and 01 are identical to file descriptor 1. Various operations (for example, exec) can associate a file descriptor with a particular file.

Some file descriptors are set up at the time the shell starts up. These are the standard input/output streams:
  • Standard input (file descriptor 0)
  • Standard output (file descriptor 1)
  • Standard error (file descriptor 2)
Commands running under the shell can use these descriptors and streams too. When a command runs under the shell, the streams are normally associated with your terminal. However, you can redirect these file descriptors to associate them with other files (so that I/O on the stream takes place on the associated file instead of your terminal). In fact, the shell lets you redirect the I/O streams associated with file descriptors 0 through 9, using the following command-line constructs.
number<file
Uses file for input on the file descriptor, the number of which is number. If you omit number, as in <file, the default is 0; this redirects the standard input.
number>file
Uses file for output on the file descriptor, the number of which is number. If you omit number, as in >file, the default is 1; this redirects the standard output. The shell creates the file if it doesn't already exist. The redirection fails if the file already exists and noclobber is set (see set).
number>|file
Is similar to number>file but if file already exists, the output written to the file overwrites its current contents.
number< >file
Uses file for input and output with the file descriptor, the number of which is number. This is most useful when the file is another terminal or modem line. If you omit number, as in < >file, the default number is zero; this redirects the standard input. Output written to the file overwrites the current contents of the file (if any). The shell creates the file if it doesn't already exist.
number>>name
Is similar to number > file, except that output is appended to the current contents of the file (if any).
number<<[-]name
Lets you specify input to a command from your terminal (or from the body of a shell script). This notation is known as a here-document. The shell reads from the standard input and feeds that as input to file descriptor number until it finds a line that exactly matches the given name. If you omit number, the default is the standard input. For example, to process the command:
cat <<abc >out
the shell reads input from the terminal until you enter a line that consists of the word abc. This input is passed as the standard input to the cat command, which then copies the text to the file out.
If any character of name is quoted or escaped, sh does not perform substitutions on the input; instead, it performs variable and command substitutions, respecting the usual quoting and escape conventions. If you put - before name, sh deletes all leading tabs in the here-document.
number1<&number2
Makes the input file descriptor number1 a duplicate of file descriptor number2. If you omit number1, the default is the standard input (file descriptor 0). For example, <&4 makes the standard input a duplicate of file descriptor 4. In this case, entering input on 4 has the same effect as entering input on the standard input.
number1>&number2
Makes the output file descriptor number2 a duplicate of file descriptor number2. If you omit number2, the default is the standard output (file descriptor 1). For example, >&2 makes the standard output a duplicate of file descriptor 2 (the standard error). In this case, writing output on the standard output has the same effect as writing output on the standard error.
number<&-
Closes input descriptor number. If you omit number, it closes the standard input.
number>&-
Closes output descriptor number. If you omit number, it closes the standard output.

Normally, redirection applies only to the command where the redirection construct appears; however, see exec.

The order of redirection specifications is significant, since an earlier redirection can affect a later one. However, these specifications can be freely intermixed with other command arguments. Since the shell takes care of the redirection, the redirection constructs are not passed to the command itself.

Note: The shell performs the implicit redirections needed for pipelines before performing any explicit redirections.

File Name Generation

The characters * ? [ are called glob characters, or wildcard characters. If an unquoted argument contains one or more glob characters, the shell processes the argument for file name generation. The glob characters are part of glob patterns, which represent file and directory names. These patterns are similar to regular expressions, but differ in syntax, since they are intended to match file names and words (not arbitrary strings). The special constructions that may appear in glob patterns are:
?
Matches exactly one character of a file name, except for the separator character / and a . at the beginning of a file name. ? only matches an actual file name character and does not match nonexistent characters at the end of the file name. ? is analogous to the metacharacter . in regular expressions.
*
Matches zero or more characters in a file name, subject to the same restrictions as ?. * is analogous to the regular expression .*.
[chars]
Defines a class of characters; the glob pattern matches any single character in the class. A class can contain a range of characters by writing the first character in the range, a dash -, and the last character. For example, [A-Za-z], in the POSIX locale, stands for all the uppercase and lowercase letters. If you want a literal - character in the class, put it as the first or last character inside the brackets. If the first character inside the brackets is an exclamation mark (!), the pattern matches any single character that is not in the class.
Some sample patterns are:
[!a-f]*.c
Matches all .c files beginning with something other than the letters from a through f.
/???/?.?
Matches all files that are under the root directory in a directory with a three-letter name, and that have a basename containing one character followed by a . followed by another single character.
*/*.[chyl]
Matches all .c, .h, .y, and .l files in a subdirectory of the working directory.
~mks/*.ksh
Matches all shell scripts in the home directory of user mks (see Directory Substitution for the use of ~).

If no files match the pattern, sh leaves the argument untouched. If the set option –f or “–o noglob” is in effect, the shell does not perform file name generation.

Variables

The shell maintains variables and can expand them where they are used in command lines; see Parameter Substitution for details.

A variable name must begin with an uppercase or lowercase letter or an underscore (_). Subsequent characters in the name, if any, can be uppercase or lowercase letters, underscores, or digits 0 through 9. You can assign a value to a variable with:
variable=value
You can implicitly declare a variable as an array by using a subscript expression when assigning a value, as in:
variable[arithmetic expression]=value

You can use a subscripted array variable anywhere that the shell allows an ordinary variable. See Arithmetic Substitution for the syntax of an arithmetic expression. Also see typeset, export, and readonly for details about the attributes of shell variables, and how shell variables can be exported to child processes.

For a list of variables that the shell either sets or understands, see Environment Variables.

Shell Execution Environments

A shell execution environment is the set of conditions affecting most commands run within the shell. It consists of:
  • Open files
  • The working directory (see cd)
  • The file creation mask (see umask)
  • The traps currently set (see trap)
  • The shell parameters (see set and export)
  • The shell functions currently defined (see Command Execution)
  • Options (see set)

A subshell environment starts as a duplicate of the shell environment, except that traps caught by the shell are set to default values in the subshell. Since the subshell environment starts as a duplicate, the value of the ENV environment variable is not run. Changes made to a subshell environment do not affect the shell environment.

Command substitutions, commands within parentheses (command), and commands to be run asynchronously (command&)—all run in subshell environments. Each command in a pipeline command|command runs in a subshell environment.

Shell utilities also run in a separate environment that does not affect the shell environment, except for certain built-in utilities (for example, cd and umask) that explicitly alter the shell environment. The environment of a shell utility is set up by the shell to include the following:
  • Open files, subject to redirection.
  • Working directory (see cd).
  • File creation mask (see umask).
  • Traps; traps caught by the shell are set to default values and traps ignored by the shell are ignored by the utility.
  • Variables defined inside the shell and having the export attribute.

Built-In Commands

This section lists the commands that are built into the shell. Such commands are built into the shell to increase performance of shell scripts or to access the shell's internal data structures and variables. These internal commands are designed to have semantics indistinguishable from external commands.

POSIX.2 recognizes a subset of these commands as special built-ins. Syntax errors in special built-in commands cause a noninteractive shell to exit with the exit status set by the command. The special built-in utilities are:

As well as built-in commands, the shell has a set of predefined aliases:

See alias for details.

Examples

Software distributed over computer networks such as Usenet is often distributed in a form known as a shell archive. In essence, a shell archive is a shell script containing the data of one or more files, plus commands to reconstruct the data files and check that the data was sent correctly. The following shows a sample shell archive:
# This is a shell archive.
# It contains the one file "frag.ksh"
# To extract contents, type
# sh file
#
if      [ -f frag.ksh ]
then    echo frag.ksh exists: will not overwrite
else
    echo extracting frag.ksh
    sed 's/^X//' >frag.ksh <<_EOF_
X# This is frag.ksh
X# Not very interesting, really.
Xecho frag.ksh here!
_EOF_
    if [ "ˋsum frag.ksh|awk '{print $1}'ˋ" !=  52575 ]
    then        echo frag.ksh damaged in transit
    fi
fi
The following is a simple script to produce as much of the Fibonacci sequence as can be calculated in integers:
# Print out Fibonacci sequence; start sequence
# with first two positional parameters:
# default 1 1
typeset –i x=${1:–1} y=${2:–1} z
while   [ x –gt 0 ]     # until overflow
do
        echo $x
        let z=y+x x=y y=z
done
The following implements the basename utility as a shell function:
# basename utility as shell function
function basename {
        case $# in
        1)      ;;
        2)      eval set \${1%$2} ;;
        *)      echo Usage: $0 pathname '[suffix]'
                return 1 ;;
        esac
        echo ${1##*/}
        return 0
}

Environment Variables

Table 2 lists the environment variables and their purposes.

Table 2. Built-in Variables
Variable Purpose
_ (Underscore) For every command that is run as a child of the shell, sh sets this variable to the full path name of the executable file and passes this value through the environment to that child process. When processing the MAILPATH variable, this variable holds the value of the corresponding mail file.
~     (Tilde) expands to value of the HOME directory.
CDPATH Contains a list of directories for the cd command to search. Directory names are separated with colons. CDPATH works like the PATH variable.
COLUMNS Used by several commands to define the width of the terminal output device.
EDITOR Specifies the default editor (either ed or sed). This variable is usually set in your .profile.
ENV sh performs parameter substitution on this value and uses the result as the name of an initialization file, or login script. This file is run with the . (dot) command; see the dot command. This variable is usually set in your .profile.
FCEDIT Contains the name of the default editor for the fc command. If this variable is not set, the default is the ed command.
HISTFILE Contains the path name of a file to be used as the history file. When the shell starts, the value of this variable overrides the default history file.
HISTSIZE Contains the maximum number of commands that the shell keeps in the history file. If this variable contains a valid number when the shell starts, it overrides the default of 127.
HOME Contains your home directory. This is also the default directory for the cd command. The HOME variable is set automatically from the Initial Working Directory field of the POSIX user database (CP directory or External Security Manager) when the user logs in.
IFS Contains a series of characters to be used as internal field separator characters. Any of these characters may separate arguments in unquoted command substitutions such as ˋcommandˋ or $(command), or in parameter substitutions. In addition, the shell uses these characters to separate values put into variables with the read command. Finally, the first character in the value of IFS separates the positional parameters in $* expansion. By default, IFS contains space, tab, and newline.
LANG Contains the default locale value.
LC_ALL Indicates the locale to be used to override any values for locale categories specified by LANG or any of the LC_ variables, such as LC_COLLATE, LC_CTYPE, and LC_MESSAGES, which a user can set and interrogate.
LINENO Contains the number of the line currently being run by a shell script.
LINES Used by several commands to define the number of lines on the terminal output device.
LOGNAME Contains the user login name. If a variable called LOGNAME exists in the CENV group of GLOBALV variables, LOGNAME is automatically set to this value. If LOGNAME does not exist in the CENV group, the LOGNAME environment variable is set to the user login name.
MAIL Contains the path name of your system mailbox. If the MAILPATH variable is not set, the OpenExtensions shell tells you when new mail arrives in this file. The shell assumes that new mail has arrived if the file modification time changes.
MBOX Contains the path name of your personal mailbox, usually $HOME/mbox, used to store messages that have been read from your system mailbox. This variable is usually set in your .profile.
MAILCHECK Contains the number of seconds of elapsed time that must pass before the system checks for mail; the default value is 600 seconds. When using the MAIL or MAILPATH variables, the OpenExtensions shell checks for mail before issuing a prompt.
MAILPATH Contains a list of mailbox files. This overrides the MAIL variable. The mailbox list is separated by colons. If any name is followed by ?message or %message, sh displays the message if the corresponding file has changed. sh performs parameter and command substitution on message, and the variable _ (temporarily) expands to the name of the mailbox file. If no ?message or % message is present, the default message is you have mail in $_.
OLDPWD Contains the name of the directory you were previously working in. The cd command sets this variable.
PATH Contains a list of directories that the system searches to find executable commands. Directories in this list are separated with colons. sh searches each directory in the order specified in the list until it finds a matching executable. If you want the shell to search the working directory, put a null string in the list of directories (for example, to tell the shell to search the working directory first, start the list with a colon or semicolon).
PID Contains the decimal value of the process ID of the parent of the shell. See ps.
PS1 Contains the primary prompt string used when the shell is interactive. The default value is a dollar sign followed by a space (). The shell expands parameters before the prompt is printed. A single exclamation mark (!) in the prompt string is replaced by the command number from the history list; see the fc command. For a real exclamation mark in the prompt, use !!. This variable is usually set in your .profile.
PS2 Contains the secondary prompt, or continuation prompt, used when completing the input of such things as reserved-word commands, quoted strings, and here documents. The default value of this variable is a greater than sign followed by a space ().
PS3 Contains the prompt string used in connection with the select reserved word. The default value is a number sign followed by a question mark and a space (#? ).
PS4 Contains the prefix for traced commands with set -x. The default value is a plus sign followed by a space (+ ).
PWD Contains the name of the working directory. When the shell starts, the working directory name is assigned to PWD unless the variable already has a value.
RANDOM Returns a random integer. Setting this variable sets a new seed for the random number generator.
SECONDS Contains elapsed time. The value of this variable grows by 1 for each elapsed second of real time. Any value assigned to this variable sets the SECONDS counter to that value; initially the shell sets the value to 0.
SHELL Contains the full path name of the current shell. It is not set by the shell, but is used by various other commands to invoke the shell. This is set automatically by the OPENVM SHELL command.
TMOUT Contains the number of seconds before user input times out. If user input has not been received within this length of time, the shell ends.
TZ Contains the system time zone value used for displaying date and time. This is set automatically from /etc/profile when the user logs in.

Files

/.sh_history
The default history storage file.
.profile
The user profile for login shell.
/etc/profile
The systemwide profile for login shells.
/tmp/sh*
Temporary files for here-documents, command substitution, history reexecution, and so on. The default directory /tmp can be overridden by setting the shell variable TMPDIR to the name of some other directory.

Localization

sh uses the following localization environment variables:
  • LANG
  • LC_ALL
  • LC_COLLATE
  • LC_CTYPE
  • LC_MESSAGES
See Localization for more information.

Exit Values

Possible exit status values are:
0
Successful completion.
1
Failure due to any of the following:
  • The shell was invoked with an incorrect option.
  • The shell was invoked to run a shell script and the command.
  • A command syntax error.
  • A redirection error.
  • A variable expansion error.

Otherwise, the exit status of the shell defaults to the exit status of the last command run by the shell. This default can be overridden by explicit use of the exit or return commands. The exit status of a pipeline is the exit status of the last command in the pipeline.

Messages and Return Codes

Ambiguous redirection
A redirection construct expanded to more than one path name.
Argument too long
Any single argument to a command is limited in length (see Limits). Command and parameter substitution may exceed this limit.
Cannot restore privileged state
This message occurs only when the implementation of POSIX does not support the saved IDs option (_POSIX_SAVED_IDS). The message is generated if you tried to use a saved ID feature to return to a privileged state.
File file already exists
You are attempting to redirect output into an existing file, but you have turned on the noclobber option (set — Set or unset command options and positional parameters). If you really want to redirect output into an existing file, use the construct >|filename, or turn off the option with:
set +o noclobber
File descriptor number already redirected
You attempted to redirect a file descriptor that was already being redirected in the same command. You can redirect a file descriptor only once.
Hangup
The shell received a hangup signal. This signal typically arises when a communication line is disconnected—for example, when a phone connection is cut off.
In base#number: base must be in [2,36]
In a number of the form base#number, the value of the base was larger than 36 or less than 2. The only valid range for bases is from 2 through 36.
Invalid subscript
A shell array was indexed with a subscript that was outside the defined bounds.
Illegal instruction
The shell received an illegal instruction signal. This signal typically occurs when a process tries to execute something that is not a valid machine instruction recognized by the hardware.
Misplaced subscript array name
The subscript for an array was missing or incorrect.
name is not an identifier
You attempted to use a nonalphanumeric name.
name: readonly variable
The given name is a read-only variable, and cannot be removed or changed (see readonly).
name: no expansion of unset variable
The shell is operating with set –u, and you used an unset variable in a substitution. For more information, see set — Set or unset command options and positional parameters.
No file descriptor available for redirection
When a file descriptor is redirected, the old value is remembered by the shell by a duplication to yet another file descriptor. The total number of file descriptors is limited by the system; hence, the shell may run out, even though your command appears to be using far fewer than the maximum number of descriptors.
Nested aliases
You have more than nine levels of aliases. For example:
alias a1=a2 a2=a3 a3=a4 ... a10=command
causes this error.
Pipe for coprocess
The shell cannot create a pipe for a coprocess. This may mean that your session or the system as a whole has already set up its maximum number of pipes.
...: restricted
If the shell has been invoked as a restricted shell, certain things are disallowed—for example, the cd command, setting PATH, and output redirection.
Temporary file error using here document
sh tried to create a temporary file holding the contents of a <<word here-document. However, the temporary file could not be created. This may indicate a lack of space on the disk where temporary files are created.
Word after ... expanded to more than one argument
In a context where only one argument was expected, a construct expanded to more than one argument.

Limits

The size of the command argument and the exported variables passed between the shell and the utilities it runs is dependent on the operating system.

A single command line is restricted to 2024 bytes.

The maximum length of an executable file name, including subdirectories and extensions, is dependent on the operating system.

Portability

POSIX.2, X/Open Portability Guide.

The construct $[arithmetic expression] is an extension of the POSIX standard.

Related Commands

alias, break, cd, continue, dot, echo, eval, exec, exit, export, fc, getopts, let, print, ps, pwd, read, readonly, return, set, shift, test, time, trap, true, typeset, unalias, unset, whence