Eval learning and application in the shell

Source: Internet
Author: User
Tags aliases arithmetic builtin eval

One, Bash command processing of 12 steps;

1. Divide the command line into tokens delimited by the fixed element character set;

SPACE, TAB, NEWLINE, ; , (, ),<, >, |,&


Token types include words, keywords, I/o redirects, and semicolons.

2. Check the first tick of each command to see if it is a keyword without quotation marks or backslashes.

If it is an open keyword, such as if and other control structure starting string, function,{or (, then the command is actually a composite command.) The shell handles the compound command internally, reads the next command, and repeats the process. A syntax error signal is given if the keyword is not a compound command start string, such as a keyword that appears in the middle of a control structure such as then.

3. Check the first keyword of each command according to the alias list;

If a match is found, the alias definition is replaced and the first step is returned, otherwise the 4th step is entered. This policy allows recursive aliases and also allows you to define keyword aliases. such as Aliasprocedure=function

4. Execute curly brace extension, e.g. a{b,c} into AB AC


5, if ~ is at the beginning of the word, replace with $home ~.

Replace ~user with the main directory of USR.

6. Execute the parameter (variable) substitution for any expression starting with the symbol $;


7, the expression of the form $ (string) to replace the command;

Here is the nested command-line processing.

8, the calculation form is $ ((string)) arithmetic expression;


9, the parameters of the line, the command and the arithmetic replacement part is divided into words again, this time it uses the characters in the $ifs to do the delimiter instead of the meta-character set of step 1;

10, to appear *,?, [/] to the execution path name extension, also known as a wildcard extension;

11, according to the Command priority table (skip aliases), for command search;

12. Execute the command after I/O redirection and other actions have been set.

Second, on the reference

1, single quotes skip the first 10 steps, cannot put single quotation marks in single quotation marks
2, double quotation mark skip step, step 9~10, that is, only deal with 6~8 steps.

In other words, double quotes ignore pipe characters, aliases, ~ substitutions, wildcard extensions, and split into words by delimiters.
Single quotes in double quotes do not work, but double quotes allow parameter substitution, command substitution, and arithmetic expression evaluation. Double quotation marks can be enclosed in double quotes, by adding the escape character "\", and also by escaping $, ', \.

Third, the role of Eval;

The role of Eval is to perform command-line processing again, that is, to perform two command-line processing on a single command line. This command should be used well, it will take some effort. Let me give you a two example.

1. Example 1: Using the eval technique to implement the shell's control structure for

Use the Eval technique to implement the shell's control structure for.

[Root@home root]# Cat Myscript1
#!/bin/sh
Evalit () {
if [$cnt = 1];then
eval [email protected]
Return
Else
Let Cnt=cnt-1
evalit [email protected]
Fi
eval [email protected]
}
Cnt=$1
echo $cnt | Egrep "^[1-9][0-9]*$" >/dev/null
If [$?-eq 0]; Then
Shift
evalit [email protected]
Else
echo ' ERROR!!! Check your input! '
Fi
[Root@home root]#./MYSCRIPT1 3 hostname
Home
Home
Home
[Root@home root]#/myscript1 5 ID |cut-f1-d "
Uid=0 (Root)
Uid=0 (Root)
Uid=0 (Root)
Uid=0 (Root)
Uid=0 (Root)


Note:There are two very special variables in bash that hold the parameter list.

$*, which holds the string group separated by the delimiter specified by $ifs.
[Email protected], the original parameter list is saved, that is, "$" "$" ...

Here I use function recursion and eval to implement the for structure.
When eval [email protected] is executed, it goes through the following steps:
1th step, split into eval [email protected]
6th step, expand [email protected] to hostname
11th step, find the built-in command eval
Repeat command-line processing, step 11th, find the hostname command, execute.

Note: Perhaps some people want to think of course, why use eval? direct [email protected] to carry out the command is OK.

Example 2: an example of a typical error

Error! Here is a typical example for everyone to look at.

[[email protected] root]# a="id | cut -f1 -d‘‘"
[[email protected] root]# $a
id:无效选项 -- f
请尝试执行‘id --help’来获取更多信息。
[[email protected] root]# eval $a
uid=0(root)


If the command line is complex (including pipes or other characters), executing the contents of a $ A string directly will cause an error. The analysis is as follows.
The processing of $a is located in the 6th step-parameter extension, that is, skipping the pipeline analysis, so "|", "cut", "-f1", "-D" has become the parameters of the ID command, of course, error.
But using eval, it took the "id", "|", "cut", "-f1", "D" strings that were processed by the command line for the first time, and once again the command line was processed, and the pipeline was analyzed correctly.

In Conclusion: to ensure that your command or script design is handled correctly by the command line, skipping any step can result in unexpected errors!

Example 3: Setting the system's LS color display

eval $(dircolors -b/etc/dircolors)


The eval statement notifies the shell to accept the eval parameter and run them again through all the steps that the command line processes.
It allows you to write scripts to arbitrarily create command strings and then pass them to the shell for execution;
$ () is the command substitution, which returns the output string of the command.
Where the dircolors command generates a bash code that sets the environment variable ls_colors according to the/etc/dircolors configuration file, as follows

[[email protected] root]# dircolors -b> tmp
[[email protected] root]# cat tmp
LS_COLORS=‘no=00:fi=00:di=01;34:ln=01; ......
export LS_COLORS
#这里我没有指定配置文件,所以dircolors按预置数据库生成代码。
其输出被eval命令传递给shell执行。


Eval is a flexible application of the Bash shell command-line processing rules to construct "smart" commands for complex functions.
The above-mentioned command is an eval of one of the most common applications, which repeats 1 command-line parameter passing procedures and executes commands purely.
In fact, it is bash's difficult point, is the Advanced Bash Programmer's compulsory skill.

Iv. Command Priority table
1. Aliases
2. Key words
3. Functions
4. Built-in commands
5. Script or executable program ($PATH)



In view of some of the confusion encountered in the study, I give some interesting commands.

1. Command builtinenable

The above command line mentions that the 11th step will be the command lookup, then what is the specific process?
Its default lookup order is functions, internal commands, scripts, and executable code. We often have to skip some of the search items in actual programming to meet certain functional requirements. This is the time to use these three commands to display Magic ~ ~

2. Command

Skips the lookup of aliases and functions, in other words, it only looks for internal commands and the scripts or executable programs found in the search path.
Here's an interesting example.

[[email protected] root]# type -all pwd
pwd is a shell builtin
pwd is /bin/pwd
[[email protected] root]# cat myscript2
#!/bin/sh
pwd(){
       echo "This is the current directory."
       command pwd
}
pwd
[[email protected] root]# ./myscript2
This is the current directory.
/root

I used the PWD () function instead of the built-in command pwd and the external command/bin/pwd, and then executed the built-in command in the script pwd. Why do we use command here? is to avoid a function falling into a recursive loop because the function name has the same name as the built-in command, and the function has a higher precedence than the built-in command.

3, Builtin

As the name implies, it only looks for built-in commands. This command is very simple, not much to say.

4. Enable

Instead of builtin, it masks a built-in command that allows you to run a shell script or executable code with the same name without giving the full pathname.
Let me give you an example.

The PWD command has two, one is shell-built, and the other is an executable program.

When some strange pathname is executed, the shell's built-in PWD prints "error message", but the external pwd prints out the "original face" of the current directory. Please see below:

[[email protected] root]# cd //
[[email protected] //]# pwd
//
[[email protected] //]# type -all pwd
pwd is a shell builtin
pwd is /bin/pwd
[[email protected] //]# /bin/pwd
/
[[email protected] //]# enable -n pwd
[[email protected] //]# pwd
/

This allows you to print out the correct path name with the external PWD after masking the built-in pwd command with Enable-n.

Bash is broad and profound, I hope you learn well. :)

Vi. about this article

This article is home_king Brother hair in linuxsir.org discussion area of a topic "BAS command line Processing" [detailed], I read this document is very good, apply to the novice, sorted out, and the paragraph has been the corresponding layout and format, in order to facilitate everyone to read;

Transferred from: http://www.linuxsir.org/main/?q=node/134

1. Eval command-line

where command- line is a plain command that is typed on the terminal. However, when you put the eval in front of it, the result is that the shell scans it two times before executing the command line. such as:

Pipe= "|"

Eval ls $pipe wc-l

When the Shell scans the command line 1 times, it replaces the pipe 's value |, and then eval makes it scan the command lines again, and the Shell takes | As the pipe symbol.

If the variable contains any characters that you want the shell to see directly on the command line (not the result of the substitution), you can use eval. command line terminator (; | &),I/o Redirection (< >) and quotation marks are symbols that have special meaning to the shell , Must appear directly on the command line.

2. Eval echo \$$# to get the last parameter

such as:cat Last

Eval echo \$$#

./last one, three four

Four

After the first scan, theshell removes the backslash. When the shell scans the row again, it replaces the value of the $4 and executes the echo command

3. The following shows how to use the eval command to create a pointer to a variable:

x=100

Ptrx=x

eval echo \$ $ptrx point to Ptrx, use this method to understand the example in b

Print

eval $ptrx =50 will be stored in the variable that Ptrx points to.

Echo $x

Print

Eval learning and application in the shell

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.