[minidive bash] Basic Features1

pinelancer·2021년 10월 23일
0

minishell

목록 보기
2/6

minishell 기능 구현에 앞서 bash manual 중요한 부분 밑줄 그어가며 읽기2

3.1.1 Shell Operation

The following is a brief description of the shell’s operation when it reads and executes a command. Basically, the shell does the following:

  1. Reads its input from a file (see Section 3.8 [Shell Scripts], page 42), from a string supplied as an argument to the -c invocation option (see Section 6.1 [Invoking Bash], page 87), or from the user’s terminal.
  2. Breaks the input into words and operators, obeying the quoting rules described in Section 3.1.2 [Quoting], page 6. These tokens are separated by metacharacters. Alias expansion is performed by this step (see Section 6.6 [Aliases], page 95).
  3. Parses the tokens into simple and compound commands (see Section 3.2 [Shell Com- mands], page 8).
  4. Performs the various shell expansions (see Section 3.5 [Shell Expansions], page 22), breaking the expanded tokens into lists of filenames (see Section 3.5.8 [Filename Expansion], page 33) and commands and arguments.
  5. Performs any necessary redirections (see Section 3.6 [Redirections], page 35) and re- moves the redirection operators and their operands from the argument list.
  6. Executes the command (see Section 3.7 [Executing Commands], page 39).
  7. Optionally waits for the command to complete and collects its exit status (see Section 3.7.5 [Exit Status], page 41).

3.1.2 Quoting

Quoting is used to remove the special meaning of certain characters or words to the shell. Quoting can be used to disable special treatment for special characters, to prevent reserved words from being recognized as such, and to prevent parameter expansion.

Each of the shell metacharacters (see Chapter 2 [Definitions], page 3) has special meaning to the shell and must be quoted if it is to represent itself. When the command history expansion facilities are being used (see Section 9.3 [History Interaction], page 149), the history expansion character, usually ‘!’, must be quoted to prevent history expansion. See Section 9.1 [Bash History Facilities], page 147, for more details concerning history expansion.

There are three quoting mechanisms: the escape character, single quotes, and double quotes.

3.1.2.1 Escape Character

A non-quoted backslash ‘\’ is the Bash escape character. It preserves the literal value of the next character that follows, with the exception of newline. If a \newline pair appears, and the backslash itself is not quoted, the \newline is treated as a line continuation (that is, it is removed from the input stream and effectively ignored).

NOT in this manual

bash-3.2$ echo

bash-3.2$ echo \	#line continued
> 

bash-3.2$ echo \n
n
bash-3.2$ echo "\n"
\n

bash-3.2$ echo $'\n'


bash-3.2$ 
#zsh
%> echo \n
n
%> echo "\n"


%>

3.1.2.2 Single Quotes

Enclosing characters in single quotes (‘’’) preserves the literal value of each character within the quotes. A single quote may not occur between single quotes, even when preceded by a backslash.

3.1.2.3 Double Quotes

Enclosing characters in double quotes (‘"’) preserves the literal value of all characters within the quotes, with the exception of ‘$’, ‘‘’, ‘\’, and, when history expansion is enabled, ‘!’. When the shell is in posix mode (see Section 6.11 [Bash POSIX Mode], page 102), the ‘!’ has no special meaning within double quotes, even when history expansion is enabled. The characters ‘$’ and ‘‘’ retain their special meaning within double quotes (see Section 3.5 [Shell Expansions], page 22). The backslash retains its special meaning only when followed by one of the following characters: ‘$’, ‘‘’, ‘"’, ‘\’, or newline. Within double quotes, backslashes that are followed by one of these characters are removed. Backslashes preceding characters without a special meaning are left unmodified. A double quote may be quoted within double quotes by preceding it with a backslash. If enabled, history expansion will be performed unless an ‘!’ appearing in double quotes is escaped using a backslash. The backslash preceding the ‘!’ is not removed.

The special parameters ‘*’ and ‘@’ have special meaning when in double quotes (see Section 3.5.3 [Shell Parameter Expansion], page 25).

3.2.2 Simple Commands

A simple command is the kind of command encountered most often. It’s just a sequence of words separated by blanks, terminated by one of the shell’s control operators (see Chapter 2 [Definitions], page 3). The first word generally specifies a command to be executed, with the rest of the words being that command’s arguments.

The return status (see Section 3.7.5 [Exit Status], page 41) of a simple command is its exit status as provided by the posix 1003.1 waitpid function, or 128+n if the command was terminated by signal n.

3.2.3 Pipelines

A pipelineis a sequence of one or more commands separated by one of the control operators‘|’ or ‘|&’.

The format for a pipeline is

[time [-p]] [!]command1[ | or |&command2] ...

...

if the pipeline is not executed asynchronously (seeSection 3.2.4 [Lists], page 9), the shell waits for all commands in the pipeline to complete.

...

The exit status of a pipeline is the exit status of the last command in the pipeline, unless the pipe fail option is enabled (seeSection 4.3.1 [The Set Builtin], page 62). If pipefailis enabled, the pipeline’s return status is the value of the last (rightmost) command to exit with a non-zero status, or zero if all commands exit successfully. If the reserved word ‘!’ precedes the pipeline, the exit status is the logical negation of the exit status as described above. The shell waits for all commands in the pipeline to terminate before returning a value

...

3.2.4 Lists of Commands

A list is a sequence of one or more pipelines separated by one of the operators ‘;’, ‘&’,‘&&’, or ‘||’, and optionally terminated by one of ‘;’, ‘&’, or anewline.

Of these list operators, ‘&&’ and ‘||’ have equal precedence, followed by ‘;’ and ‘&’, which have equal precedence.

Commands separated by a ‘;’ are executed sequentially; the shell waits for each command to terminate in turn. The return status is the exit status of the last command executed.

and and or lists are sequences of one or more pipelines separated by the control oper- ators ‘&&’ and ‘||’, respectively. and and or lists are executed with left associativity.

n and list has the form command1 && command2
command2 is executed if, and only if, command1 returns an exit status of zero (success).

An or list has the formcommand1 || command2
command2 is executed if, and only if, command1 returns a non-zero exit status.

The return status of and and or lists is the exit status of the last command executed in the list.

3.2.5 Compound Commands

Compound commands are the shell programming language constructs. Each construct begins with a reserved word or control operator and is terminated by a corresponding reserved word or operator.

( expression )
Returns the value of expression. This may be used to override the normal precedence of operators.

expression1 && expression2
True if both expression1 and expression2 are true

expression1 || expression2
True if either expression1 or expression2 is true.

The && and || operators do not evaluate expression2 if the value of expression1 is sufficient to determine the return value of the entire conditional expression.

3.4 Shell Parameters

A parameter is an entity that stores values. It can be a name, a number, or one of the special characters listed below. A variable is a parameter denoted by a name. A variable has a value and zero or more attributes. Attributes are assigned using the declare builtin command (see the description of the declare builtin in Section 4.2 [Bash Builtins], page 51).

A parameter is set if it has been assigned a value. The null string is a valid value. Once a variable is set, it may be unset only by using the unset builtin command.

If value is not given, the variable is assigned the null string.

A variable may be assigned to by a statement of the form
name=[value]

If value is not given, the variable is assigned the null string. All values undergo tilde expansion, parameter and variable expansion, command substitution, arithmetic expansion, and quote removal (detailed below). If the variable has its integer attribute set, then value is evaluated as an arithmetic expression even if the $((...)) expansion is not used (see Section 3.5.5 [Arithmetic Expansion], page 31). Word splitting is not performed, with the exception of "$@" as explained below. Filename expansion is not performed. Assign- ment statements may also appear as arguments to the alias, declare, typeset, export, readonly, and local builtin commands (declaration commands). When in posix mode (see Section 6.11 [Bash POSIX Mode], page 102), these builtins may appear in a command after one or more instances of the command builtin and retain these assignment statement properties.

...

3.4.1 Positional Parameters

A positional parameter is a parameter denoted by one or more digits, other than the single digit 0. Positional parameters are assigned from the shell’s arguments when it is invoked, and may be reassigned using the set builtin command. Positional parameter N may be referenced as ${N}, or as $N when N consists of a single digit. Positional parameters may not be assigned to with assignment statements. The set and shift builtins are used to set and unset them (see Chapter 4 [Shell Builtin Commands], page 44). The positional parameters are temporarily replaced when a shell function is executed (see Section 3.3 [Shell Functions], page 18).

When a positional parameter consisting of more than a single digit is expanded, it must be enclosed in braces.

NOT in this manual

bash-3.2$ cat > ech.sh
bash-3.2$ echo $1; echo $11; echo ${11} <C-d>
bash-3.2$ bash ech.sh 0 1 2 3 4 5 6 7 8 9 10 
0
01 <= ${1}1
10

3.4.2 Special Parameters

  • *

    ($*) Expands to the positional parameters, starting from one. When the ex- pansion is not within double quotes, each positional parameter expands to a separate word. In contexts where it is performed, those words are subject to fur- ther word splitting and filename expansion. When the expansion occurs within double quotes, it expands to a single word with the value of each parameter separated by the first character of the IFS special variable. That is, "$*" is equivalent to "$1c$2c...", where c is the first character of the value of the IFS variable. If IFS is unset, the parameters are separated by spaces. If IFS is null, the parameters are joined without intervening separators.

  • [...]

3.5 Shell Expansion

Expansion is performed on the command line after it has been split into tokens. There are seven kinds of expansion performed:

  • brace expansion

  • tilde expansion

  • parameter and variable expansion

  • command substitution

  • arithmetic expansion

  • word splitting

  • filename expansion

The order of expansions is: brace expansion; tilde expansion, parameter and variable ex- pansion, arithmetic expansion, and command substitution (done in a left-to-right fashion); word splitting; and filename expansion.

NOT in this manual

	brace expansion 
=> 	tilde expansion
=> 	parameter and variable expansion
=> 	arithmetic expansion
=> 	command substisution(done in a left-to-right fashion)
=> 	word splitting
=> 	filename expansion

On systems that can support it, there is an additional expansion available: process substitution. This is performed at the same time as tilde, parameter, variable, and arith- metic expansion and command substitution.

After these expansions are performed, quote characters present in the original word are removed unless they have been quoted themselves (quote removal).

Only brace expansion, word splitting, and filename expansion can increase the number of words of the expansion; other expansions expand a single word to a single word. The only exceptions to this are the expansions of "$@" and $ (see Section 3.4.2 [Special Parameters], page 21), and "${name[@]}" and ${name[]} (see Section 6.7 [Arrays], page 96).

After all expansions, quote removal (see Section 3.5.9 [Quote Removal], page 35) is performed.

...

3.5.7 Word Splitting

The shell scans the results of parameter expansion, command substitution, and arithmetic expansion that did not occur within double quotes for word splitting.

The shell treats each character of $IFS as a delimiter, and splits the results of the other expansions into words using these characters as field terminators. If IFS is unset, or its value is exactly \<space>\<tab>\<newline>, the default, then sequences of \<space>, \<tab>, and \<newline> at the beginning and end of the results of the previous expansions are ignored, and any sequence of IFS characters not at the beginning or end serves to delimit words. If IFS has a value other than the default, then sequences of the whitespace characters space, tab, and newline are ignored at the beginning and end of the word, as long as the whitespace character is in the value of IFS (an IFS whitespace character). Any character in IFS that is not IFS whitespace, along with any adjacent IFS whitespace characters, delimits a field. A sequence of IFS whitespace characters is also treated as a delimiter. If the value of IFS is null, no word splitting occurs.

Explicit null arguments ("" or ’’) are retained and passed to commands as empty strings. Unquoted implicit null arguments, resulting from the expansion of parameters that have no values, are removed. If a parameter with no value is expanded within double quotes, a null argument results and is retained and passed to a command as an empty string. When a quoted null argument appears as part of a word whose expansion is non-null, the null argument is removed. That is, the word -d’’ becomes -d after word splitting and null argument removal.

NOT in this manual

#normal
bash-3.2$ echo 12
12

#null removed
bash-3.2$ echo 1""2
12

#passed to a command as an empty string
bash-3.2$ echo 1 "" 2
1  2

Note that if no expansion occurs, no splitting is performed.

3.5.8 Filename Expansion

After word splitting, unless the -f option has been set (see Section 4.3.1 [The Set Builtin], page 62), Bash scans each word for the characters ‘*’, ‘?’, and ‘[’. If one of these characters appears, and is not quoted, then the word is regarded as a pattern, and replaced with an alphabetically sorted list of filenames matching the pattern (see Section 3.5.8.1 [Pattern Matching], page 33). If no matching filenames are found, and the shell option nullglob is disabled, the word is left unchanged. If the nullglob option is set, and no matches are found, the word is removed. If the failglob shell option is set, and no matches are found, an error message is printed and the command is not executed. If the shell option nocaseglob is enabled, the match is performed without regard to the case of alphabetic characters.

When a pattern is used for filename expansion, the character ‘.’ at the start of a filename or immediately following a slash must be matched explicitly, unless the shell option dotglob is set. The filenames ‘.’ and ‘..’ must always be matched explicitly, even if dotglob is set. In other cases, the ‘.’ character is not treated specially.

When matching a filename, the slash character must always be matched explicitly by a slash in the pattern, but in other matching contexts it can be matched by a special pattern character as described below (see Section 3.5.8.1 [Pattern Matching], page 33).

...

3.5.8.1 Pattern Matching

Any character that appears in a pattern, other than the special pattern characters described below, matches itself. The nul character may not occur in a pattern. A backslash escapes the following character; the escaping backslash is discarded when matching. The special pattern characters must be quoted if they are to be matched literally.

The special pattern characters have the following meanings:

  • * $(*)

    Matches any string, including the null string. When the globstar shell option is enabled, and ‘’ is used in a filename expansion context, two adjacent ‘’s used as a single pattern will match all files and zero or more directories and subdirectories. If followed by a ‘/’, two adjacent ‘*’s will match only directories and subdirectories.

...

3.5.9 Quote Removal

After the preceding expansions, all unquoted occurrences of the characters ‘\’, ‘ ’ ’, and ‘ " ’ that did not result from one of the above expansions are removed.

밑줄 모음

  • Quoting

    There are three quoting mechanisms: the escape character, single quotes, and double quotes.

  • Escape Character

    non-quoted backslash ‘\’ is the Bash escape character. It preserves the literal value of the next character that follows, with the exception of newline

  • Single Quotes:
    Enclosing characters in single quotes (‘’’) preserves the literal value of each character within the quotes.

  • Double Quotes:
    Enclosing characters in double quotes (‘"’) preserves the literal value of all characters within the quotes, with the exception of ‘$’, ‘‘’, ‘\’

  • Simple commands

    It’s just a sequence of words separated by blanks, terminated by one of the shell’s control operators. The first word generally specifies a command to be executed, with the rest of the words being that command’s arguments.

  • Pipelines

    A pipelineis a sequence of one or more commands separated by one of the control operators‘|’ or ‘|&’.

    if the pipeline is not executed asynchronously (seeSection 3.2.4 [Lists], page 9), the shell waits for all commands in the pipeline to complete.

    The exit status of a pipeline is the exit status of the last command in the pipeline

  • Lists of commands

    A list is a sequence of one or more pipelines separated by one of the operators ‘;’, ‘&’,‘&&’, or ‘||’, and optionally terminated by one of ‘;’, ‘&’, or a newline.

  • Shell parameters

    A parameter is an entity that stores values.

    The null string is a valid value. Once a variable is set, it may be unset only by using the unset builtin command.

    If value is not given, the variable is assigned the null string. All values undergo tilde expansion, parameter and variable expansion, command substitution, arithmetic expansion, and quote removal (detailed below).

  • Shell Expansion

    Expansion is performed on the command line after it has been split into tokens. There are seven kinds of expansion performed:

    • brace expansion

    • tilde expansion

    • parameter and variable expansion

    • command substitution

    • arithmetic expansion

    • word splitting

    • filename expansion

      The order of expansions is: brace expansion; tilde expansion, parameter and variable ex- pansion, arithmetic expansion, and command substitution (done in a left-to-right fashion); word splitting; and filename expansion.

      Only brace expansion, word splitting, and filename expansion can increase the number of words of the expansion; other expansions expand a single word to a single word.

      The only exceptions to this are the expansions of "$@" and $* ... .

      After all expansions, quote removal (see Section 3.5.9 [Quote Removal], page 35) is performed.

  • Word Splitting

    The shell scans the results of parameter expansion, command substitution, and arithmetic expansion that did not occur within double quotes for word splitting.

    ... $IFS as a delimiter ...

    If IFS is unset, or its value is exactly \<space>\<tab>\<newline>, the default

    If the value of IFS is null, no word splitting occurs.

    a null argument results and is retained and passed to a command as an empty string. When a quoted null argument appears as part of a word whose expansion is non-null, the null argument is removed.

#normal
bash-3.2$ echo 12
12

#null removed
bash-3.2$ echo 1""2
12

#passed to a command as an empty string
bash-3.2$ echo 1 "" 2
1  2

Reference

GNU Bash manual

profile
🏃🏾

0개의 댓글