bash coding.



Know how to code bash flow of control statements : The test-command can be a actual command or even sequence of commands that will be run and the final return code tested. You may also use the test command which can either be invoked with the command test or be invoked with the open and closed square brackets, []. If using the brackets, remember to keep white-space on both sides of both open and closed brackets.
if
if test-cmd
then
  action
fi
if test-cmd
then
  action

else
  action 2
fi
if test-cmd
then
  action

elif test-cmd2
then
  action 2
fi
if test-cmd
then
  action

elif test-cmd2
then
  action 2

else
  action 3
fi
if test-cmd
then
  action

elif test-cmd2
then
  action 2

elif test-cmd2
then
  action 3
fi
if test-cmd
then
  action

elif test-cmd2
then
  action 2

elif test-cmd2
then
  action 3

else
  action 4
fi

while and until
while test-cmd
do
  action1
done
until test-cmd
do
  action1
done
read -p "y or n : " ans
while [ $ans != "n" ]
do
  read -p "y or n : " ans
done
read -p "y or n : " ans
until [ $ans = "n" ]
do
  read -p "y or n : " ans
done
while test if test-cmd is true, and until test if test-cmd is false. continue - used in middle of a loop action block to return to the top of the loop rather than completing the rest of the block. break - used in middle of a loop action block to terminate the loop and out the bottom.
#prompt user
read -p "y or n : " ans

# create an endless loop 
while [ 1 == 1 ]
do
  if [ "$ans" = "y" ]
  then
    # break out of loop 
    break;
  elif [ "$ans" = "n" ]
  then
    # Reprompt user and continue 
    read -p "You sure ? y or n : " ans
    continue;
  fi
   
  # Repromt user with problem, loops back to top.
  read -p "Answer not valid, use y or n : " ans

done
break and continue work on only the innermost loop. So, if loops are embedded, additional action may be required.
case case is a string matching if structure. It tests the contents of a string against a series of alternative values or patterns. case can use the file-name style wildcards to create flexible pattern descriptions. Each match is exclusive. Each match is exact. So use wild cards if partial match is OK. Best practice is to match specifics first and then use more general patterns to catch more general matches. It is a safe practice to quote variable being tested.
case "$var" in
  template-1 )
    action[s]
  ;;
  template-2 )
    action[s]
  ;;
  ...
esac
case "$ans" in
  123 )
    echo "Exactly 123"
  ;;
  
  123* )
    echo "Starts with  123"
  ;;

  456|654 )
    echo "Either 456 or 654"

  ;;

  [0-9][0-9][0-9] )
    echo "Some other three digit number"
    echo "values of 123, 456, 654, or starting with 123"
    echo "would have been caught by a previous case"
  ;;

  ??? )
    echo "A three character string.
    # This should catch 3 any three character ans, except for
    #   digits because we've already tested for those.
  ;;

  [0-9][0-9][0-9]* )
    echo "A longer string that starts with three numbers."
    # Remember this is file-name wild-card, NOT regexp.  
    # * is any characters of any number. 
    # This will match any values starting with starting with
    #   three digits except 123 because they would have been
    #   matched above. 
  ;;
 
  * )

    echo "Any string that has not been previously matched"
  ;;
esac

Code a function. The following forms work : function funName ( ) { actions; } funName () { actions; } function funName { actions; } Also, once bash recognizes function declaration, these are valid arrangements function funName { action; } funName () { action; action; } Access command line arguments from inside function. $0 - function name. $# - argument count $1,$2,$3 - specific arguments. ${10} - arguments > 9. shift - discard argument 1 and shifts down all other arguments. In the old Bourne shell, this was one of the few ways to access an argument > $9. return x # returns an numeric value 0-255 of user's choice. This can be tested/assigned in calling program. 0 considered success and can be tested with if, while, and until. All other values considered fail. return is used only in a function. exit is used to terminate the program and if used inside a function, it will terminate the program.
function filecount ()
{ 
  if [ $# -lt 1 ]
  then
    echo "no file list"
    # set function arguments to list of current directory.
    set `ls` 

  # create an endless loop 
  while [ $# -gt 0 ]
  do
    wc $1
    shift

    read -p "Continue ? y or n : " ans
    if [ "$ans" = "n" ]
    then
      # break out of loop 
      break;
    elif [ "$ans" = "y" ]
    then
      # go back to top and continue.
      # If list is zero, the while loop will exit normally
      continue;
    fi
   
    # If invalid response, terminate program
    echo "Answer not valid. "
    exit 1

  done
  return 0
}

for loops bash provides 2 types of for loops. The list for comes from the original Bourne shell. for fn in e1 e2 e3 e4 do action on $fn done for, in, do, done are keywords fn is a variable of your choosing that will be assigned the next element of the list each time through the loop. e1 e2 e3 e4 is a list of values to assign to the variable. This list may be literal or it may be generated by a command. The list for will assigne
# for each file in current directory
for fn in `ls`
do
  # if the file is regular and readable
  if test -f $fn && test -r $fn
  then
    # do a word count on it.
    wc $fn
  fi
done
The other for form is borrowed from the C language.
#!/bin/bash

declare -a randArray

# generate 10 random numbers.
for (( ndx=1; ndx < 10; ndx++ ))
{
# $RANDOM is a shell defined variable that returns a
#   pseudo-random number.
randArray[$ndx]=$RANDOM
}

echo ${randArray[*]}


select loop
# Use select to display the contents of $HOME/Backup
#   Use command substitution to get contents of Backup  
#   add quit to that list
# 
#  Put the selected string in the variable fn
select fn in $(ls ~/Backup) quit
do
  # show which list string was chosen
  echo $fn

  # if choice was quit, then break out of loop.
  if [ "$fn" == quit ]
  then
    break
  fi

  # trim the final extension off of the retrieved filename
  #   if it has an 11 digit extension.
  rfn=$(echo "$fn" | sed "s/\.[0-9]\{11\}$//")
  # show results
  echo $rfn
done
The select loop takes a list of strings which it numbers and displays, followed by a question mark prompt. A list can be a specified sequence of strings. And/Or you may use command substitution to generate a list of strings. e.g. $( ls $HOME/Backup ) List is numbered in order that is specified in the select statement. The user may pick any of the listed strings by selecting a number. The string from the list is assigned to the variable named in the select statement. An invalid selection will cause the queston prompt to redisplay. Hitting [enter] with no choice will cause the numbered list to redisplay. Once a choice has been made, execution enters the body of the loop where you can processes the string stored in the specified variable. Note, you need to code a break, return, or exit, depending on situation to leave the loop. Examples of test questions.
Regular expressions http://faculty.cs.niu.edu/~berezin/330/Q/regex-q.html http://faculty.cs.niu.edu/~berezin/330/N/regex-intro.html Keep in mind, most programs will attempt to make the largest match possible to a regular expressions, so .* # will match a whole line. literals - most characters are treated as literals. But some are not. This may sometimes required a backslash to suppress meaning. Anchors ^ - the caret or circumflex at beginning of expressions represents beginning of line. $ - at end of expression represents end of line. \< - represents beginning of word, a-zA-Z0-9_ valid word characters. \> - represents end of word. Beginning and end of word markers do not have to be used together. Regular expression matches . - period, one character of any type. [13579] - brackets, one character, list characters to match. Spaces and commas are treated as literals. [[:upper:]] - predefined symbolic sets that can be used. [^char-list] - the caret at the start of the character list creates a NOT condition, match a character not in list. Operators - modify the previous character expression. * - asterisk, repeater of previous regular expression zero or more times. This repeats the regular expression before matching. \{#\} \{#,\} \{#,#\} - specific multiplier. Repeats previous character # number of times. Usually used with anchors to limit larger matches. \( \) - parentheses - groups and remembers a match to regular expression inside of parentheses. The matched string can be recalled with \1, etc. Parentheses sets sequentially numbered from left. Parentheses can also be used by grep to list alternative matches.
function ask {

read -p "up or down : " ans
if echo $ans | grep '\(up\|down\)' > /dev/null 2>&1
then
   echo good answer
else
   echo "What's $ans"
fi
}
 
Not all programs that use regular expressions may use all of them. Some may have additional expressions, and some may requires backslashes where others don't. * although actually part of the extended regular expressions, the following may also work, if done as shown. \+ # represents one or more occurences of previous character. \? # represents zero or one occurence of previous character.
Extended regular expressions. + - plus, one or more of previous expression. ? - zero or 1 occurrences of characters matching regular expression. (regex|regex) - list alternative expressions. If this is active \(\) won't be. {str1,str2,st3} - list alternative possible matches, if this active, \{\} won't be.
sed specific. http://faculty.cs.niu.edu/~berezin/330/Q/sed-1-q.html http://faculty.cs.niu.edu/~berezin/330/Q/sed-addr-q.html s/regex/replacement/[#g] - substitute 1st match to regular expression with literal. The standard delimiter is the / but any character immediately following the s becomes the delimiter of that substitution statement. A number will specify a match other than the 1st one and a g represents all occurrences on the line. s/regex/replacement/p - prints out the line after successful substitution. This is in addition to normal sed behavior. s/regex/replacement/w file - will write to a file. Once files are open during current sed execution, all output is appended. But rerunning the sed command will overwrite existing file. \(\) - parentheses can be used on left hand side to copy matched expressions. \1, \2, etc. - can be used on left or right hand side to recall matched expressions. & - on right hand side will recall whole match to regular expression even if \( \) not used. Line addressing. Specific line addresses and regular expressions can be used to address target lines independent of action to be taken. 1 - literal valid line number, number too large just not matched. $ - last line in file. /regex/ - line that has a match to regular expression. /regex1/,/regex2/ - match range of lines, start and stop match included in matched lines. In sed, matches can be turned on and off several times. line numbers and regular expressions can be mixed. 3,/^bob/ - from line 3 to the an occurrence of bob at start of line. NOT ! - the not will invert the test condition but it is applied to the action. 3,/^bob/ !s/bill/dean/ - apply substitution to all lines except lines 3 to the occurrence of the line starting with bob.
ISO-OSI layers Application, Presentation, Session, Transport, Network, Data link, Physical Internet protocol layers. Application, Transport, Network, Link. Link layer. Physical circuitry, bit level signals. hardware machine access code (MAC) protocols 802.11 WiFi, CSMA/CA 802.3 Ethernet, CSMA/CD Uses a frame to hold the TCP/IP packet. Holds the source MAC# and destination MAC# of either target system or gateway out of local network. Frames are not transmitted past gateway, but are stripped and new frame appropriate to next hop's technology created. Network layer. IP (Internet protocol) level. Uses an IP packet to move along Internet. Contains source and destination IPs of communicating end-points. IPv4 uses a 4 Octet number designation. IPv4 is mainly class based, A,B,C Variable length headers. Packets may be fragmented if a particular hop can not handle current packet size. IPv4 uses a TTL count to guard against lost packets. TTL counts both number of hops and time spent being delivered. IPv6 uses a pair of 128 bit source and destination addresses. Each address is 2 part 64-bit sub-net ID - specifies domain to contact. 64-bit interface identified - specifies specific system to contact. IPv6 is classless - all domains get a 64-bit identifier. IPv6 packet headers are 40 octet in size but can have a linked set of options fields between header and packet body. Uses hop count only. Time spent being delivered no longer watched. Both IPv4 and IPv6 contain a field indicating the type of (TCP) transport layer packet encapsulated in the IP packet. There are about 142 protocols currently defined. Some are obsolete. Transport layer Transport layer deals with final delivery a communication transaction across the Internet. The TCP layer usually contains the Port IDs of the source and destination applications. Application layer. Prgrams such as PuTTY, Filezilla, Cuteftp, Outlook, Firefox, etc.
ISO-OSI model - a theoretical model of network communication function. Modern technolgy merges several of the layers. Application Presentation Session Transport Network Data Link Physical Networking