This commit is contained in:
gferg 2003-09-15 14:30:43 +00:00
parent dbc098bbd4
commit 702659bde7
5 changed files with 391 additions and 60 deletions

View File

@ -6,6 +6,66 @@
http://personal.riverusers.com/~thegrendel/Change.log
------------------------------------------------------------------------
Version 2.1
'HUCKLEBERRY' release, 09/14/03
1) In Appendix B, "Reference Cards:
Fixups --
(thanks to errors brought to my attention by Heiner Steven).
2) In Appendix B, "Reference Cards:
Added "Miscellaneous Construct" table.
Added variable prefix matching to "Parameter Substitution" table.
3) In "Internal Variables" chapter"
Noted that "$*" must be quoted to differentiate it from "$@" variable,
and added a case to "arglist.sh" example to demonstrate this.
(Thanks, Heiner Steven.)
4) In "Command Substitution" chapter:
Added note about the invocation of a subshell.
Likewise added note in "setting variable to a file" in-line example.
(Thanks, Paul Heffner.)
Removed erroneous comment from in-line example of
setting a variable to contents of a file.
(Thanks, Anthony Richardson.)
5) In "Arrays" chapter:
Added "script-array.sh" example.
(Thanks, Chris Martin, for the inspiration.)
6) In "System Resources" subsection of "System and Administrative
Commands":
Fixed minor error ("while 1") in 'ulimit' illustrative script.
(Thanks Emmanuel Chantreau)
7) In "Subshells" chapter:
Added a paragraph of commentary concerning external commands and Bash
builtins.
8) In "Special Characters" chapter:
Elaborated example of ';' usage.
9) In "Gotchas" chapter:
Added in-line example of problem caused by piping to a loop.
(Thanks Anthony Richardson.)
10) In "System and Administrative Commands" chapter:
Added more info to "sar" listing.
11) In "Writing Scripts" section of "Exercises" appendix:
Added "Monitoring Processes" exercise.
12) In "Recursion" section of "Oddities" chapter:
Added Anthony Richardson's "usrmnt.sh" example.
(Thanks!)
13) Slight modifications to certain example files for clarification.
Version 2.0
'GOOSEBERRY' release, 08/24/03
@ -52,7 +112,7 @@ bumped up to a major version. This is now officially a "mature" project.
by disabling parameter substitution within the body of a 'here document.'
(Thanks, Albert Reiner, for the idea.)
10) In "Miscellaneous" subsection of "System and Administrative Commands"
10) In "Miscellaneous" subsection of "System and Administrative Commands":
chapter:
Added listing for "dialog" toolsets.

View File

@ -272,6 +272,8 @@ Uncomment line below to generate index.
<!ENTITY directoryinfo SYSTEM "directory-info.sh">
<!ENTITY embarr SYSTEM "embedded-arrays.sh">
<!ENTITY generatescript SYSTEM "generate-script.sh">
<!ENTITY scriptarray SYSTEM "script-array.sh">
<!ENTITY usrmnt SYSTEM "usrmnt.sh">
<!ENTITY dialog SYSTEM "dialog.sh">
<!ENTITY evalex SYSTEM "eval.example">
<!ENTITY namesdata SYSTEM "names.data">
@ -294,8 +296,8 @@ Uncomment line below to generate index.
</affiliation>
</author>
<releaseinfo>2.0</releaseinfo>
<pubdate>24 August 2003</pubdate>
<releaseinfo>2.1</releaseinfo>
<pubdate>14 September 2003</pubdate>
<revhistory>
@ -420,8 +422,15 @@ Uncomment line below to generate index.
<date>24 August 2003</date>
<authorinitials>mc</authorinitials>
<revremark>'GOOSEBERRY' release: Major update.</revremark>
</revision>
<revision>
<revnumber>2.1</revnumber>
<date>14 September 2003</date>
<authorinitials>mc</authorinitials>
<revremark>'HUCKLEBERRY' release: bugfixes and more material.</revremark>
</revision>
</revhistory>
@ -445,7 +454,7 @@ Uncomment line below to generate index.
linkend="bzipref">bzip2-ed</link> <quote>tarball</quote>
including both the SGML source and
rendered HTML, may be downloaded from <ulink
url="http://personal.riverusers.com/~thegrendel/abs-guide-2.0.tar.bz2">
url="http://personal.riverusers.com/~thegrendel/abs-guide-2.1.tar.bz2">
the author's home site</ulink>. See the <ulink
url="http://personal.riverusers.com/~thegrendel/Change.log">change
log</ulink> for a revision history.</para>
@ -979,7 +988,17 @@ echo $(( 2#101011 )) # Base conversion, not a comment.
the same line.</para>
</formalpara>
<para><programlisting>echo hello; echo there</programlisting></para>
<para>
<programlisting>echo hello; echo there
if [ -x "$filename" ]; then # Note that "if" and "then" need separation.
# Why?
echo "File $filename exists."; cp $filename $filename.bak
else
echo "File $filename not found."; touch $filename
fi; echo "File test complete."</programlisting>
</para>
<para>Note that the <quote><token>;</token></quote> sometimes
needs to be <link linkend="escp">escaped</link>.</para>
@ -6016,9 +6035,9 @@ echo "Last command argument processed = $last_cmd_arg"
</indexterm>
<listitem><para></para>
<para>The <varname>$PPID</varname> of a process is
the process id (<varname>pid</varname>) of its parent process.
the process ID (<varname>pid</varname>) of its parent process.
<footnote><para>The pid of the currently running script is
<footnote><para>The PID of the currently running script is
<varname>$$</varname>, of course.</para></footnote>
</para>
@ -6428,8 +6447,10 @@ echo "Last command argument processed = $last_cmd_arg"
<secondary>positional</secondary>
<tertiary>all</tertiary>
</indexterm>
<listitem><para>All of the positional parameters, seen as a single
word</para>
<listitem>
<para>All of the positional parameters, seen as a single word</para>
<note><para><quote><varname>$*</varname></quote> must be
quoted.</para></note>
</listitem>
</varlistentry>
@ -6446,12 +6467,18 @@ echo "Last command argument processed = $last_cmd_arg"
<primary>positional parameter</primary>
<secondary>all</secondary>
</indexterm>
<listitem><para>Same as <token>$*</token>, but each parameter is a
<listitem>
<para>Same as <token>$*</token>, but each parameter is a
quoted string, that is, the parameters are passed on
intact, without interpretation or expansion. This means,
among other things, that each parameter in the argument
list is seen as a separate word.</para>
<note><para>Of course, <quote><varname>$@</varname></quote>
should be quoted.</para></note>
<example id="arglist">
<title><command>arglist</command>: Listing arguments with $* and $@</title>
<programlisting>&arglist;</programlisting>
@ -9607,7 +9634,7 @@ do
operation-2
...
operation-n
# Need a way to break out of loop.
# Need a way to break out of loop or script will hang.
done</programlisting></para>
</listitem>
@ -9993,7 +10020,7 @@ wait</programlisting>
process</quote>, that is, a process whose <link
linkend="forkref">parent</link> has terminated, cannot be
killed (you can't kill something that is already dead),
but <command>init</command> will usually clean it up
but <command>init</command> will generally clean it up
sooner or later.</para></note>
</listitem>
@ -10159,6 +10186,8 @@ wait</programlisting>
<chapter id="external">
<title>External Filters, Programs and Commands</title>
<para><anchor id="externalref"></para>
<para>Standard UNIX commands make shell scripts more versatile. The
power of scripts comes from coupling system commands and shell
directives with simple programming constructs.</para>
@ -16366,11 +16395,13 @@ exit 0
<secondary>system activity report</secondary>
</indexterm>
<listitem>
<para>Invoking <command>sar</command> (system activity report)
gives a very detailed rundown on system statistics.
This command is found on some commercial UNIX
systems, but is not part of the base Linux
distribution. It is contained in the <ulink
<para>Invoking <command>sar</command> (System Activity Reporter)
gives a very detailed rundown on system statistics. The
Santa Cruz Operation (SCO) released
<command>sar</command> as Open Source in June, 1999.</para>
<para>This command is not part of the base Linux distribution,
but may be obtained as part of the<ulink
url="http://perso.wanadoo.fr/sebastien.godard/">
sysstat utilities</ulink> package, written by <ulink
url="mailto:sebastien.godard@wanadoo.fr">Sebastien
@ -16519,7 +16550,7 @@ exit 0
<listitem>
<para><replaceable>P</replaceable>rocess
<replaceable>S</replaceable>tatistics: lists currently
executing processes by owner and PID (process id). This
executing processes by owner and PID (process ID). This
is usually invoked with <option>ax</option> options,
and may be piped to <link linkend="grepref">grep</link>
or <link linkend="sedref">sed</link> to search for a
@ -16632,12 +16663,12 @@ exit 0
<secondary>process id</secondary>
</indexterm>
<listitem>
<para>Identifies <emphasis>process id (pid)</emphasis> of a
<para>Identifies <emphasis>process ID (PID)</emphasis> of a
running job. Since job control commands, such as <link
linkend="killref">kill</link> and <command>renice</command>
act on the <emphasis>pid</emphasis> of a process (not
act on the <emphasis>PID</emphasis> of a process (not
its name), it is sometimes necessary to identify that
<emphasis>pid</emphasis>. The <command>pidof</command>
<emphasis>PID</emphasis>. The <command>pidof</command>
command is the approximate counterpart to the <link
linkend="ppidref">$PPID</link> internal variable.</para>
@ -16665,7 +16696,7 @@ exit 0
<secondary>fuser</secondary>
</indexterm>
<listitem>
<para>Identifies the processes (by pid) that are accessing
<para>Identifies the processes (by PID) that are accessing
a given file, set of files, or directory. May also be
invoked with the <option>-k</option> option, which kills
those processes. This has interesting implications for
@ -17552,8 +17583,10 @@ then
<para>
<programlisting>#!/bin/bash
# This script is for illustrative purposes only.
# Run it at your own peril -- it *will* freeze your system.
while 1 # Endless loop.
while true # Endless loop.
do
$0 & # This script invokes itself . . .
#+ forks an infinite number of times . . .
@ -17620,7 +17653,7 @@ exit 0 # Will not exit here, because this script will never terminate.</pr
<para>Get info about or make changes to root device, swap space, or video
mode. The functionality of <command>rdev</command> has generally been taken over by
<command>lilo</command>, but <command>rdev</command> remains
useful for setting up a ram disk. This is another dangerous command, if misused.
useful for setting up a ram disk. This is a dangerous command, if misused.
</para>
</listitem>
</varlistentry>
@ -17957,6 +17990,10 @@ echo $textfile_listing2
# Thanks, S.C.</programlisting>
</para>
<note><para>Command substitution invokes a <link
linkend="subshellsref">subshell</link>.</para></note>
<caution><para>Command substitution may result in word splitting.
<programlisting>COMMAND `echo a b` # 2 args: a and b
@ -18043,13 +18080,12 @@ echo "$dir_listing" # quoted
linkend="catref">cat</link> command.</para>
<para>
<programlisting>variable1=`&lt;file1` # Set "variable1" to contents of "file1".
variable2=`cat file2` # Set "variable2" to contents of "file2".
<programlisting>variable1=`&lt;file1` # Set "variable1" to contents of "file1".
variable2=`cat file2` # Set "variable2" to contents of "file2".
# This, however, forks a new process,
#+ so the line of code executes slower than the above version.
# Note 1:
# Removes newlines.
#
# Note 2:
# Note:
# The variables may contain embedded whitespace,
#+ or even (horrors), control characters.</programlisting>
</para>
@ -18159,7 +18195,6 @@ File_contents1=$(cat $file1)
File_contents2=$(&lt;$file2) # Bash permits this also.</programlisting></para></note>
<para>Examples of command substitution in shell scripts:
<orderedlist>
<listitem><para><xref linkend="bingrep"></para></listitem>
@ -19627,9 +19662,19 @@ echo a111b | gawk '/a1+b/'
<emphasis>subshells</emphasis> let the script do
parallel processing, in effect executing multiple subtasks
simultaneously.</para>
<sidebar>
<para>In general, an <link linkend="externalref">external
command</link> in a script <link linkend="forkref">forks
off</link> a subprocess, whereas a Bash <link
linkend="builtinref">builtin</link> does not. For this reason,
builtins execute more quickly than their external command
equivalents.</para>
</sidebar>
<variablelist id="subshellparens">
<title><anchor id="subshellparens1">Command List in Parentheses</title>
<title><anchor id="subshellparens1">Command List in
Parentheses</title>
<varlistentry>
<term>( command1; command2; command3; ... )</term>
@ -20733,6 +20778,14 @@ echo ${array2[2]} #
echo ${array2[3]} # fourth element</programlisting>
</para>
<para><link linkend="commandsubref">Command substitution</link> can
construct the individual elements of an array.</para>
<example id="scriptarray">
<title>Loading the contents of a script into an array</title>
<programlisting>&scriptarray;</programlisting>
</example>
<para>In an array context, some Bash <link
linkend="builtinref">builtins</link> have a slightly altered
meaning. For example, <link linkend="unsetref">unset</link>
@ -22005,11 +22058,55 @@ exit 0</programlisting>
<programlisting>&badread;</programlisting>
</example>
<para>In fact, as Anthony Richardson points out, piping to
<emphasis>any</emphasis> loop can cause a similar problem.</para>
<para>
<programlisting># Loop piping troubles.
# This example by Anthony Richardson.
foundone=false
find $HOME -type f -atime +30 -size 100k |
while true
do
read f
echo "$f is over 100KB and has not been accessed in over 30 days"
echo "Consider moving the file to archives."
foundone=true
done
# foundone will always be false here since it is
#+ set to true inside a subshell
if [ $foundone = false ]
then
echo "No files need archiving."
fi
# =====================Now, here is the correct way:=================
foundone=false
for f in $(find $HOME -type f -atime +30 -size 100k) # No pipe here.
do
echo "$f is over 100KB and has not been accessed in over 30 days"
echo "Consider moving the file to archives."
foundone=true
done
if [ $foundone = false ]
then
echo "No files need archiving."
fi</programlisting>
</para>
<para>--</para>
<para>Using <quote>suid</quote> commands within scripts is risky,
as it may compromise system security.
<footnote><para>Setting the <emphasis>suid</emphasis> permission on
the script itself has no effect.</para></footnote>
</para>
</para>
<para>Using shell scripts for CGI programming may be problematic. Shell
script variables are not <quote>typesafe</quote>, and this can cause
@ -22478,6 +22575,11 @@ test "$city" \< Paris && echo "Yes, Paris is greater than $city" # Greater ASCI
<programlisting>&pbook;</programlisting>
</example>
<example id="usrmnt">
<title>Another (useful) script that recursively calls itself</title>
<programlisting>&usrmnt;</programlisting>
</example>
<caution><para>Too many levels of recursion can exhaust the
script's stack space, causing a segfault.</para></caution>
@ -23337,12 +23439,13 @@ fi</programlisting>
good book on the subject? I was looking to buy a tutorial and
reference covering all aspects of the subject. I was looking for a
book that would take difficult concepts, turn them inside out, and
explain them in excruciating detail with well-commented examples.
explain them in excruciating detail, with well-commented examples.
<footnote><para>This is the notorious <quote>flog it to
death</quote> technique.</para></footnote>
In fact, I was looking for this very book, or something much
like it. Unfortunately, it didn't exist, and if I wanted it,
I'd have to write it. And so, here we are, folks.</para>
In fact, I was looking for <emphasis>this very book</emphasis>,
or something much like it. Unfortunately, it didn't exist,
and if I wanted it, I'd have to write it. And so, here we are,
folks.</para>
<para>This reminds me of the apocryphal story about the mad
professor. Crazy as a loon, the fellow was. At the sight of a
@ -23353,7 +23456,7 @@ fi</programlisting>
write a book with the very same title. When he died some years
later, he allegedly had several thousand books to his credit,
probably putting even Asimov to shame. The books might not have
been any good, who knows, but does that really matter? Here's
been any good -- who knows -- but does that really matter? Here's
a fellow who lived his dream, even if he was obsessed by it,
driven by it, and I can't help admiring the old coot...</para>
@ -23373,7 +23476,7 @@ fi</programlisting>
HOW-2 Meet Women: The Shy Man's Guide to
Relationships</ulink>. He has also written the <ulink
url="http://tldp.org/HOWTO/Software-Building-HOWTO.html">Software-Building
HOWTO</ulink>.</para>
HOWTO</ulink>. Lately, he has been trying his hand at short fiction.</para>
<para>A Linux user since 1995 (Slackware 2.2, kernel 1.2.1),
the author has emitted a few
@ -23543,11 +23646,11 @@ fi</programlisting>
were Gabor Kiss, Leopold Toetsch, Peter Tillier, Marcus Berglof,
Tony Richardson, Nick Drage (script ideas!), Rich Bartell, Jess
Thrysoee, Adam Lazur, Bram Moolenaar, Baris Cicek, Greg Keraunen,
Keith Matthews, Sandro Magi, Albert Reiner, Dim Segebart,
Rory Winston, Lee Bigelow, Wayne Pollock, <quote>jipe</quote>,
Emilio Conti, Dennis Leeuw, Dan Jacobson, Aurelio Marinho Jargas,
Edward Scholtz, Jean Helou, and David Lawyer (himself an author
of 4 HOWTOs).</para>
Keith Matthews, Sandro Magi, Albert Reiner, Dim Segebart, Rory
Winston, Lee Bigelow, Wayne Pollock, <quote>jipe,</quote> Emilio
Conti, Dennis Leeuw, Dan Jacobson, Aurelio Marinho Jargas,
Edward Scholtz, Jean Helou, Chris Martin, and David Lawyer
(himself an author of 4 HOWTOs).</para>
<para>My gratitude to <ulink url="mailto:chet@po.cwru.edu">Chet
Ramey</ulink> and Brian Fox for writing <command>Bash</command>,
@ -24341,6 +24444,10 @@ fi</programlisting>
<appendix id="refcards">
<title>Reference Cards</title>
<para>The following reference cards provide a useful
<emphasis>summary</emphasis> of certain scripting concepts.
The foregoing text treats these matters in more depth and gives
usage examples.</para>
<table pgwide=0>
<title>Special Shell Variables</title>
@ -24373,11 +24480,11 @@ fi</programlisting>
<entry>Number of positional parameters</entry>
</row>
<row>
<entry><option>$*</option></entry>
<entry>All the positional parameters (as a single word)</entry>
<entry><option>"$*"</option></entry>
<entry>All the positional parameters (as a single word) *</entry>
</row>
<row>
<entry><option>$@</option></entry>
<entry><option>"$@"</option></entry>
<entry>All the positional parameters (as separate strings)</entry>
</row>
<row>
@ -24415,6 +24522,9 @@ fi</programlisting>
</tgroup>
</table>
<para><command>*</command> <emphasis>Must be quoted</emphasis>,
otherwise it defaults to
<quote><varname>$@</varname></quote>.</para>
<table>
@ -24459,7 +24569,7 @@ fi</programlisting>
<entry><option>-ne</option></entry>
<entry>Not equal to</entry>
<entry></entry>
<entry><option>!</option></entry>
<entry><option>!=</option></entry>
<entry>Not equal to</entry>
</row>
<row>
@ -24670,6 +24780,7 @@ fi</programlisting>
<entry>Value of <parameter>var</parameter>, same as
<parameter>$var</parameter></entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry><option>${var-DEFAULT}</option></entry>
<entry>If <parameter>var</parameter> not set, evaluate expression
@ -24677,9 +24788,11 @@ fi</programlisting>
</row>
<row>
<entry><option>${var:-DEFAULT}</option></entry>
<entry>If <parameter>var</parameter> not set, evaluate expression
as <parameter>$DEFAULT</parameter> *</entry>
<entry>If <parameter>var</parameter> not set or is empty,
evaluate expression as <parameter>$DEFAULT</parameter>
*</entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry><option>${var=DEFAULT}</option></entry>
<entry>If <parameter>var</parameter> not set, evaluate expression
@ -24690,6 +24803,7 @@ fi</programlisting>
<entry>If <parameter>var</parameter> not set, evaluate expression
as <parameter>$DEFAULT</parameter> *</entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry><option>${var+OTHER}</option></entry>
<entry>If <parameter>var</parameter> set, evaluate expression as
@ -24700,6 +24814,7 @@ fi</programlisting>
<entry>If <parameter>var</parameter> set, evaluate expression as
<parameter>$OTHER</parameter>, otherwise as null string</entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry><option>${var?ERR_MSG}</option></entry>
<entry>If <parameter>var</parameter> not set, print
@ -24710,6 +24825,17 @@ fi</programlisting>
<entry>If <parameter>var</parameter> not set, print
<parameter>$ERR_MSG</parameter> *</entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry><option>${!varprefix*}</option></entry>
<entry>Matches all previously declared variables beginning with
<parameter>varprefix</parameter></entry>
</row>
<row>
<entry><option>${!varprefix@}</option></entry>
<entry>Matches all previously declared variables beginning with
<parameter>varprefix</parameter></entry>
</row>
</tbody>
</tgroup>
</table>
@ -24735,12 +24861,12 @@ fi</programlisting>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry><option>{$string:position}</option></entry>
<entry><option>${string:position}</option></entry>
<entry>Extract substring from <parameter>$string</parameter>
at <parameter>$position</parameter></entry>
</row>
<row>
<entry><option>{$string:position:length}</option></entry>
<entry><option>${string:position:length}</option></entry>
<entry>Extract <parameter>$length</parameter>
characters substring from <parameter>$string</parameter>
at <parameter>$position</parameter></entry>
@ -24856,6 +24982,120 @@ fi</programlisting>
<emphasis>regular expression</emphasis>.</para>
<table pgwide=0>
<title>Miscellaneous Constructs</title>
<tgroup cols="2">
<thead>
<row>
<entry>Expression</entry>
<entry>Interpretation</entry>
</row>
</thead>
<tbody>
<row><entry></entry><entry></entry></row>
<row>
<entry>Brackets</entry><entry></entry>
</row>
<row>
<entry><option>if [ CONDITION ]</option></entry>
<entry>Test construct</entry>
</row>
<row>
<entry><option>if [[ CONDITION ]]</option></entry>
<entry>Extended test construct</entry>
</row>
<row>
<entry><option>Array[1]=element1</option></entry>
<entry>Array initialization</entry>
</row>
<row>
<entry><option> [a-z]</option></entry>
<entry>Range of characters within a Regular Expression</entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry>Curly Brackets</entry><entry></entry>
</row>
<row>
<entry><option>${variable}</option></entry>
<entry>Parameter substitution</entry>
</row>
<row>
<entry><option>${!variable}</option></entry>
<entry>Indirect variable reference</entry>
</row>
<row>
<entry><option>{ command1; command2 }</option></entry>
<entry>Block of code</entry>
</row>
<row>
<entry><option>{string1,string2,string3,...}</option></entry>
<entry>Brace expansion</entry>
</row>
<row><entry></entry><entry></entry></row>
<row><entry></entry><entry></entry></row>
<row>
<entry>Parentheses</entry><entry></entry>
</row>
<row>
<entry><option>( command1; command2 )</option></entry>
<entry>Command group executed within a subshell</entry>
</row>
<row>
<entry><option>Array=(element1 element2 element3)</option></entry>
<entry>Array initialization</entry>
</row>
<row>
<entry><option>result=$(COMMAND)</option></entry>
<entry>Execute command in subshell and assign result to
variable</entry>
</row>
<row>
<entry><option>&gt;(COMMAND)</option></entry>
<entry>Process substitution</entry>
</row>
<row>
<entry><option>&lt;(COMMAND)</option></entry>
<entry>Process substitution</entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry>Double Parentheses</entry><entry></entry>
</row>
<row>
<entry><option>(( var = 78 ))</option></entry>
<entry>Integer arithmetic</entry>
</row>
<row>
<entry><option>var=$(( 20 + 5 ))</option></entry>
<entry>Integer arithmetic, with variable assignment</entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry>Quoting</entry><entry></entry>
</row>
<row>
<entry><option>"$variable"</option></entry>
<entry>"Weak" quoting</entry>
</row>
<row>
<entry><option>'string'</option></entry>
<entry>"Strong" quoting</entry>
</row>
<row><entry></entry><entry></entry></row>
<row>
<entry>Back Quotes</entry><entry></entry>
</row>
<row>
<entry><option>result=`COMMAND`</option></entry>
<entry>Execute command in subshell and assign result to variable</entry>
</row>
</tbody>
</tgroup>
</table>
</appendix>
<!-- Reference Cards appendix -->
@ -26484,6 +26724,20 @@ Smith,Tom,404 Polk Ave.,Los Angeles,CA,90003,(213) 879-5612
</listitem>
</varlistentry>
<varlistentry>
<term><command>Monitoring Processes</command></term>
<listitem>
<para>Write a script to continually monitor all running
processes and to keep track of how many child processes each
parent spawns. If a process spawns more than five children,
then the script sends an e-mail to the system administrator
(or root) with all relevant information, including the
time, PID of the parent, PIDs of the children, etc. The
script writes a report to a log file every ten minutes.
</para>
</listitem>
</varlistentry>
<varlistentry>
<term><command>Strip Comments</command></term>
<listitem>
@ -26886,6 +27140,7 @@ B. Distribution of the work or derivative of the work in any standard
<para>Linux is a trademark registered to Linus Torvalds.</para>
<para>Unix and UNIX are trademarks registered to the Open Group.</para>
<para>MS Windows is a trademark registered to the Microsoft Corp.</para>
<para>Scrabble is a trademark registered to Hasbro, Inc.</para>
<para>All other commercial trademarks mentioned in the body of this work
are registered to their respective owners.</para>
</sidebar>

View File

@ -1,4 +1,5 @@
#!/bin/bash
# arglist.sh
# Invoke this script with several arguments, such as "one two three".
E_BADARGS=65
@ -35,4 +36,12 @@ echo "Arg list seen as separate words."
echo
echo "Listing args with \$* (unquoted):"
for arg in $*
do
echo "Arg #$index = $arg"
let "index+=1"
done # Unquoted $* sees arguments as separate words.
echo "Arg list seen as separate words."
exit 0

View File

@ -5,8 +5,8 @@ echo -n "What is your favorite vegetable? "
read
echo "Your favorite vegetable is $REPLY."
# REPLY holds the value of last "read" if and only if
# no variable supplied.
# REPLY holds the value of last "read" if and only if
#+ no variable supplied.
echo
echo -n "What is your favorite fruit? "
@ -14,8 +14,8 @@ read fruit
echo "Your favorite fruit is $fruit."
echo "but..."
echo "Value of \$REPLY is still $REPLY."
# $REPLY is still set to its previous value because
# the variable $fruit absorbed the new "read" value.
# $REPLY is still set to its previous value because
#+ the variable $fruit absorbed the new "read" value.
echo

View File

@ -1,7 +1,9 @@
#!/bin/bash
# t-out.sh (per a suggestion by "syngin seven)
# t-out.sh
# Inspired by a suggestion from "syngin seven" (thanks).
TIMELIMIT=4 # 4 seconds
TIMELIMIT=4 # 4 seconds
read -t $TIMELIMIT variable <&1
@ -15,3 +17,8 @@ else
fi
exit 0
# Exercise for the reader:
# -----------------------
# Why is the redirection (<&1) necessary in line 8?
# What happens if it is omitted?