📄 _chapter 1.htm
字号:
background processing. While the child shell works, the parent normally sleeps.
(See <span class="docEmphasis">wait,</span> below.)</p>
<center>
<h5 id="ch01fig03" class="docFigureTitle">Figure 1.3. The <span class="docEmphasis">fork</span>
system call.</h5>
<p class="docText">
<img alt="graphics/01fig03.gif" src="01fig03.gif" border="0" width="500" height="284"></p>
</center>
<p class="docText"><span class="docEmphStrong">The <span class="docEmphasis">
wait</span> System Call. </span>The parent shell is programmed to go to sleep
(wait) while the child takes care of details such as handling redirection,
pipes, and background processing. The <span class="docEmphasis">wait</span>
system call causes the parent process to suspend until one of its children
terminates. If <span class="docEmphasis">wait</span> is successful, it returns
the PID of the child that died and the child's exit status. If the parent does
not wait and the child exits, the child is put in a zombie state (suspended
animation) and will stay in that state until either the parent calls
<span class="docEmphasis">wait</span> or the parent dies.<span id="ENB1-3"><a class="docLink" href="#EN1-3"><sup>[3]</sup></a></span>
If the parent dies before the child, the <span class="docEmphasis">init</span>
process adopts any orphaned zombie process. The <span class="docEmphasis">wait</span>
system call, then, is not just used to put a parent to sleep, but also to ensure
that the process terminates properly. </p>
<p class="docText"><span class="docEmphStrong">The <span class="docEmphasis">
exec</span> System Call. </span>After you enter a command at the terminal, the
shell normally forks off a new shell process: the child process. As mentioned
earlier, the child shell is responsible for causing the command you typed to be
executed. It does this by calling the <span class="docEmphasis">exec</span>
system call. Remember, the user command is really just an executable program.
The shell searches the path for the new program. If it is found, the shell calls
the <span class="docEmphasis">exec</span> system call with the name of the
command as its argument. The kernel loads this new program into memory in place
of the shell that called it. The child shell, then, is overlaid with the new
program. The new program becomes the child process and starts executing.
Although the new process has its own local variables, all environment variables,
open files, signals, and the current working directory are passed to the new
process. This process exits when it has finished, and the parent shell wakes up.</p>
<p class="docText"><span class="docEmphStrong">The <span class="docEmphasis">
exit</span> System Call. </span>A new program can terminate at any time by
executing the <span class="docEmphasis">exit</span> call. When a child process
terminates, it sends a signal (<span class="docEmphasis">sigchild</span>) and
waits for the parent to accept its exit status. The exit status is a number
between 0 and 255. An exit status of zero indicates that the program executed
successfully, and a nonzero exit status means that the program failed in some
way.</p>
<p class="docText">For example, if the command <span class="docEmphasis">ls</span>
had been typed at the command line, the parent shell would
<span class="docEmphasis">fork</span> a child process and go to sleep. The child
shell would then <span class="docEmphasis">exec</span> (overlay) the
<span class="docEmphasis">ls</span> program in its place. The
<span class="docEmphasis">ls</span> program would run in place of the child,
inheriting all the environment variables, open files, user information, and
state information. When the new process finished execution, it would exit and
the parent shell would wake up. A prompt would appear on the screen, and the
shell would wait for another command. If you are interested in knowing how a
command exited, each shell has a special built-in variable that contains the
exit status of the last command that terminated. (All of this will be explained
in detail in the individual shell chapters.) See
<a class="docLink" href="#ch01fig04">Figure 1.4</a> for an example of process
creation and termination.</p>
<center>
<h5 id="ch01fig04" class="docFigureTitle">Figure 1.4. The <span class="docEmphasis">fork, exec,
wait,</span> and <span class="docEmphasis">exit</span> system calls.</h5>
<p class="docText">
<img alt="graphics/01fig04.gif" src="01fig04.gif" border="0" width="500" height="414"></p>
</center>
<div align="center">
<center>
<table cellSpacing="0" width="90%" border="1" style="border-collapse: collapse" bordercolor="#111111" cellpadding="5">
<tr>
<td>
<h2 class="docSidebarTitle">EXPLANATION</h2>
<span style="FONT-WEIGHT: bold">
<ol class="docList" type="1">
<li><span style="FONT-WEIGHT: normal">
<p class="docList">The parent shell creates a copy of itself with the
<span class="docEmphasis">fork</span> system call. The copy is called the
child shell.</span></li>
<li><span style="FONT-WEIGHT: normal">
<p class="docList">The child shell has a new PID and is a copy of its
parent. It will share the CPU with the parent.</span></li>
<li><span style="FONT-WEIGHT: normal">
<p class="docList">The kernel loads the <span class="docEmphasis">grep</span>
program into memory and executes (<span class="docEmphasis">exec</span>)
it in place of the child shell. The <span class="docEmphasis">grep</span>
program inherits the open files and environment from the child.</span></li>
<li><span style="FONT-WEIGHT: normal">
<p class="docList">The <span class="docEmphasis">grep</span> program
exits, the kernel cleans up, and the parent is awakened.</span></li>
</ol>
</span></td>
</tr>
</table>
</center>
</div>
<h5 id="ch01list02" class="docExampleTitle">Example 1.2 </h5>
<pre>(C Shell)
1 % <span class="docEmphStrong">cp filex filey</span>
% <span class="docEmphStrong">echo $status</span>
<span class="docEmphasis">0</span>
2 % <span class="docEmphStrong">cp xyz</span>
<span class="docEmphasis">Usage: cp [-ip] f1 f2; or: cp [-ipr] f1 ... fn d2</span>
% <span class="docEmphStrong">echo $status</span>
<span class="docEmphasis">1</span>
(Bourne and Korn Shells)
3 $ <span class="docEmphStrong">cp filex filey</span>
$ <span class="docEmphStrong">echo $?</span>
<span class="docEmphasis">0</span>
$ <span class="docEmphStrong">cp xyz</span>
<span class="docEmphasis">Usage: cp [-ip] f1 f2; or: cp [-ipr] f1 ... fn d2</span>
$ <span class="docEmphStrong">echo $?</span>
<span class="docEmphasis">1</span></pre>
<div align="center">
<center>
<table cellSpacing="0" width="90%" border="1" style="border-collapse: collapse" bordercolor="#111111" cellpadding="5">
<tr>
<td>
<h2 class="docSidebarTitle">EXPLANATION</h2>
<span style="FONT-WEIGHT: bold">
<ol class="docList" type="1">
<li><span style="FONT-WEIGHT: normal">
<p class="docList">The <span class="docEmphasis">cp</span> (copy)
command is entered at the C shell command line prompt. After the command
has made a copy of <span class="docEmphasis">filex</span> called
<span class="docEmphasis">filey,</span> the program exits and the prompt
appears. The csh <span class="docEmphasis">status</span> variable
contains the exit status of the last command that was executed. If the
status is zero, the <span class="docEmphasis">cp</span> program exited
with success. If the exit status is nonzero, the
<span class="docEmphasis">cp</span> program failed in some way.</span></li>
<li><span style="FONT-WEIGHT: normal">
<p class="docList">When entering the <span class="docEmphasis">cp</span>
command, the user failed to provide two filenames: the source and
destination files. The <span class="docEmphasis">cp</span> program sent
an error message to the screen and exited with a status of one. That
number is stored in the csh <span class="docEmphasis">status</span>
variable. Any number other than zero indicates that the program failed.</span></li>
<li><span style="FONT-WEIGHT: normal">
<p class="docList">The Bourne and Korn shells process the
<span class="docEmphasis">cp</span> command as the C shell did in the
first two examples. The only difference is that the Bourne and Korn
shells store the exit status in the <span class="docEmphasis">?</span>
variable, rather than the <span class="docEmphasis">status</span>
variable.</span></li>
</ol>
</span></td>
</tr>
</table>
</center>
</div>
<h3 class="docSection1Title" id="ch01lev1sec4">1.4 The Environment and Inheritance</h3>
<p class="docText">When you log on, the shell starts up and inherits a number of
variables, I/O streams, and process characteristics from the
<span class="docEmphasis">/bin/login</span> program that started it. In turn, if
another shell is spawned (forked) from the login or parent shell, that child
shell (<span class="docEmphasis">subshell</span>) will inherit certain
characteristics from its parent. A subshell may be started for a number of
reasons: for handling background processing, for handling groups of commands, or
for executing scripts. The child shell inherits an environment from its parent.
The environment consists of process permissions (who owns the process), the
working directory, the file creation mask, special variables, open files, and
signals.</p>
<h4 class="docSection2Title" id="ch01lev2sec10">1.4.1 Ownership</h4>
<p class="docText">When you log on, the shell is given an identity. It has a
real user identification (<span class="docEmphasis">UID</span>), one or more
real group identifications (<span class="docEmphasis">GID</span>), and an
effective user identification and effective group identification (<span class="docEmphasis">EUID</span>
and <span class="docEmphasis">EGID</span>). The EUID and EGID are initially the
same as the real UID and GID. These ID numbers are found in the
<span class="docEmphasis">passwd</span> file and are used by the system to
identify users and groups. The EUID and EGID determine what permissions a
process has access to when reading, writing, or executing files. If the EUID of
a process and the real UID of the owner of the file are the same, the process
has the owner's access permissions for the file. If the EGID and real GID of a
process are the same, the process has the owner's group privileges.</p>
<p class="docText">The real UID, from the <span class="docEmphasis">/etc/passwd</span>
file, is a positive integer associated with your login name. The real UID is the
third field in the password file. When you log on, the login shell is assigned
the real UID and all processes spawned from the login shell inherit its
permissions. Any process running with a UID of zero belongs to root (the
superuser) and has root privileges. The real group identification, the GID,
associates a group with your login name. It is found in the fourth field of the
password file.</p>
<p class="docText">The EUID and EGID can be changed to numbers assigned to a
different owner. By changing the EUID (or EGID<span id="ENB1-4"><a class="docLink" href="#EN1-4"><sup>[4]</sup></a></span>)
to another owner, you can become the owner of a process that belongs to someone
else. Programs that change the EUID or EGID to another owner are called
<span class="docEmphasis">setuid</span> or <span class="docEmphasis">setgid</span>
programs. The <span class="docEmphasis">/bin/passwd</span> program is an example
of a <span class="docEmphasis">setuid</span> program that gives the user root
privileges. <span class="docEmphasis">Setuid</span> programs are often sources
for security holes. The shell allows you to create <span class="docEmphasis">
setuid</span> scripts, and the shell itself may be a <span class="docEmphasis">
setuid</span> program.</p>
<h4 class="docSection2Title" id="ch01lev2sec11">1.4.2 The File Creation Mask</h4>
<p class="docText">When a file is created, it is given a set of default
permissions. These permissions are determined by the program creating the file.
Child processes inherit a default mask from their parents. The user can change
the mask for the shell by issuing the <span class="docEmphasis">umask</span>
command at the prompt or by setting it in the shell's initialization files. The
<span class="docEmphasis">umask</span> command is used to remove permissions
from the existing mask.</p>
<p class="docText">Initially, the <span class="docEmphasis">umask</span> is 000,
giving a directory 777 (<span class="docEmphasis">rwxrwxrwx</span>) permissions
and a file 666 (<span class="docEmphasis">rw杛w杛w
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -