Please contact or Mt Xia for assistance with all your shell programming needs.
3. POSITIONAL PARAMETERSA BourneShell script can also read in command-line arguments. The first argument is referred to as $1, the second is $2, and so on. Command-line arguments are referred to as positional parameters. Let's look at an example BourneShell script to see how these are used. Sample Session: $cat neat_shell echo $1 $2 $3 echo $0 is the name of the shell script echo "There were $# arguments." echo $* $ Insure that the BourneShell script is executable by issuing this command: Sample Session: $chmod a+x neat_shell $ Now, if we type the name of the BourneShell script with no arguments, we get the following results. Sample Session: $neat_shell neat_shell is the name of the shell script There were 0 arguments. $ In this sample session, there were no arguments given so none were printed. $0 is the positional parameter that refers to the name of the script. Since there were no arguments given with this invocation of neat_shell, there were zero arguments listed.
3.1 Reading Input Into a Shell VariableThe BourneShell script can read user input from standard input. The read command will read one line from standard input and assign the line to one or more variables. The following example shows how this works. Sample Session: $cat read_script echo "Please enter a string of your choice" read a echo $a $ This simple script will read one line from standard input (keyboard) and assign it to the variable a. Sample Session: $read_script Please enter a string of your choice Here it is Here it is $ The line read from standard input can also be assigned to several variables as shown in the following example. Sample Session: $cat reads echo "Please enter three strings" read a b c echo $a $b $c echo $c echo $b echo $a $ This time, we will turn on the trace mechanism and follow the execution of this BourneShell script. Sample Session: $sh -x reads + echo Please enter three strings Please enter three strings + read a b c this is more than three strings + echo this is more than three strings this is more than three strings + echo more than three strings more than three strings + echo is is + echo this this $ It is interesting to note that the spaces separate the values for the variables a,b, and c. For example, the variable a was assigned the string this, the variable b was assigned the string is, and the remainder of the line was assigned to c (including the spaces). Sample Session: $cat read_ex echo 'Enter line: \c' read line echo "The line was: $line" $ In this example, the \c option will suppress the carriage return. The single quote marks protect the backslash from being interpreted by the shell. Also notice that the double quote marks have no effect on the substitution of the variable line. Sample Session: $read_ex Enter line: All's well that ends well The line was: All's well that ends well $
3.2 Command SubstitutionYou can execute a command by enclosing it within two grave accent marks [these are sometimes called backquotes (`)]. The BourneShell will replace the command and the grave marks with the output from the command. Sample Session: $cat dir dir=`pwd` echo 'You are using the' $dir 'directory' $ NOTE: The grave marks lean to the left, and the apostrophes lean to the right. The grave marks enclose the pwd command. Sample Session: $dir You are using the /user0/rharding directory $ The important thing to notice here is that the pwd command was executed; and the output, /user0/rharding, was then assigned to the variable dir. It is not necessary to assign the output of a command to a variable as shown in the previous example. The command substitution can occur directly as shown in the next example. Sample Session: $cat dir2 echo 'You are using the' `pwd` 'directory' $dir2 You are using the /user0/rharding directory $ One final example will show a practical use of command substitution. This BourneShell script will use the date command to provide the date in a useful format. The normal output from the date command looks like the following. Sample Session: $date Wed Sep 12 18:02:05 MDT 1990 $ Here's a BourneShell script that rearranges the output into a more useable format. Sample Session: $cat dateset set `date` echo $* echo echo 'Argument 1:' $1 echo 'Argument 2:' $2 echo 'Argument 3:' $3 echo 'Argument 4:' $4 echo echo $2 $3, $6 $dateset Wed Sep 12 18:02:05 MDT 1990 Argument 1: Wed Argument 2: Sep Argument 3: 12 Argument 4: 18:02:05 Sep 12, 1990 $ The first command in the BourneShell script dateset uses the grave accent marks to set the command-line argument variables to the output of the date command. The next commands show the first four of these argument variables. The final command displays the arguments in a different order that could be useful in a report or a letter. 3.3 Comments in BourneShell Scripts Comments can be inserted into the BourneShell script by beginning each comment line with the pound symbol (#) or a colon (:). All characters after the comment character will be ignored by the shell. The only exception to this rule is that the first character of the first line must not be a pound symbol; if the first character is a pound sign, the BourneShell tries to execute the script as if it was written in CShell syntax. Sample Session: $cat com_sub # The first line sets your present working directory # to the variable 'directory' directory=`pwd` # The second line sets the date to the variable 'when' when=`date` : The third line will echo on the screen echo "You are in $directory on $when" : You could have said echo : : "You are in `pwd` on `date`" : to have a one line program $
3.4 BourneShell Environment - Exporting VariablesWithin a process, you can declare, initialize, read, and modify variables. The variable is local to that process. When a process forks a child process, the parent process does not automatically pass the value of the variable to the child process. Here is an example of the variables not being exported. Sample Session: $cat no_export car=mercedes # set the variable echo $0 $car $$ # $0 = name of file executed # $car =value of variable car # $$ = PID number (process id) inner # execute another BourneShell script echo $0 $car $$ # display same as above $cat inner echo $0 $car $$ # display variables for this process $chmod a+x no_export $chmod a+x inner $no_export no_export mercedes 4790 inner 4792 no_export mercedes 4790 $ When no_export was executed, it, of course, assigned a value of mercedes to the variable car and printed it out. The call to inner created a child process. Its PID is 4792, while the parent PID is 4790. Notice, when inner tried to print the value of car, it printed nothing. The reason is because the value of car was not passed by the parent. Can the value be passed from parent to child process? Yes, by using the export command. Let's look at an example. Sample Session: $cat export_it car=mercedes export car echo $0 $car $$ inner1 echo $0 $car $$ $cat inner1 echo $0 $car $$ car=chevy echo $0 $car $$ $chmod a+x export_it $chmod a+x inner1 $export_it export_it mercedes 4798 inner1 mercedes 4800 inner1 chevy 4800 export_it mercedes 4798 $ In the export_it BourneShell script, the variable car was initialized to mercedes; and then it was exported. This means that the value of car is now available to a child process. When inner1 prints out the value of car it has the value of mercedes. This is as we expect because the value of car was exported from the parent. The next line of inner1 changes the value of car to chevy. This is shown in the next line of the sample session. The last line of the session shows the return to the parent process and the value is still mercedes. How is this possible? Exporting variables is only valid from the parent to the child process. The child process cannot change the parent's variable.
Workshop 3This workshop will reinforce your understanding of the ideas presented in Chapter 3. Login to the Multimax using the username and password given to you by the instructor. Each student is to complete the entire workshop. DESK EXERCISES 1. What is the positional parameter that represents the name of the command? 2. What positional parameter stands for the number of arguments on the command line? 3. What command will read one line from standard input and assign the value to a variable? 4. What character is used to indicate command substitution? 5. What are the two characters that indicate comments in BourneShell scripts? 6. Why is it bad practice to put a pound sign (#) in the first character position of the first line of a BourneShell script? 7. Variables set by the parent process are automatically known to the child process. True/False 8. What command will allow the value of a variable to be passed to a child process? 9. Can a child process change the value of the parents' variable? Why? COMPUTER EXERCISES 10. Write a BourneShell script called "reverse_it" that has three strings as parameters and then display the strings in opposite order. Be sure to include appropriate comments. Hint: positional parameters 11. Write a BourneShell script called "read_it" that does the same as question 10 but prompts the user to enter each string separately. How would you trace the execution of this script. Do it! Continue on the next page. 12. Write a BourneShell script that uses the output of the "date" command and changes it from: Wed Sep 12 18:02:05 MDT 1990 to: Sep 12, 1990 18:02:05