diff options
Diffstat (limited to 'chapter07/functions.xml')
-rw-r--r-- | chapter07/functions.xml | 451 |
1 files changed, 451 insertions, 0 deletions
diff --git a/chapter07/functions.xml b/chapter07/functions.xml new file mode 100644 index 000000000..e46522c0f --- /dev/null +++ b/chapter07/functions.xml @@ -0,0 +1,451 @@ +<sect1 id="ch07-functions"> +<title>Creating the functions script</title> + +<para> +Create a new file <filename>/etc/init.d/functions</filename> containing +the following: +</para> + +<literallayout> + +<userinput>cat > functions << "EOF"</userinput> +#!/bin/sh +# Begin /etc/init.d/functions + +# +# Set a few variables that influence the text that's printed on the +# screen. The SET_COL variable starts the text in column number 70 (as +# defined by the COL variable). NORMAL prints text in normal mode. +# SUCCESS prints text in a green colour and FAILURE prints text in a red +# colour +# + +COL=70 +SET_COL="echo -en \\033[${COL}G" +NORMAL="echo -en \\033[0;39m" +SUCCESS="echo -en \\033[1;32m" +FAILURE="echo -en \\033[1;31m" + +# +# The evaluate_retval function evaluates the return value of the process +# that was run just before this function was called. If the return value +# was 0, indicating success, the print_status function is called with +# the 'success' parameter. Otherwise the print_status function is called +# with the failure parameter. +# + +evaluate_retval() +{ + if [ $? = 0 ] + then + print_status success + else + print_status failure + fi +} + +# +# The print_status prints [ OK ] or [FAILED] to the screen. OK appears +# in the colour defined by the SUCCESS variable and FAILED appears in +# the colour defined by the FAILURE variable. Both are printed starting +# in the colomn defined by the COL variable. +# + +print_status() +{ + +# +# If no parameters are given to the print_status function, print usage +# information. +# + + if [ $# = 0 ] + then + echo "Usage: print_status {success|failure}" + return 1 + fi + + case "$1" in + success) + $SET_COL + echo -n "[ " + $SUCCESS + echo -n "OK" + $NORMAL + echo " ]" + ;; + failure) + $SET_COL + echo -n "[" + $FAILURE + echo -n "FAILED" + $NORMAL + echo "]" + ;; + esac + +} + +# +# The loadproc function starts a process (often a daemon) with +# proper error checking +# + +loadproc() +{ + +# +# If no parameters are given to the print_status function, print usage +# information. + +# + + if [ $# = 0 ] + then + echo "Usage: loadproc {program}" + exit 1 + fi +# +# Find the basename of the first parameter (the daemon's name without +# the path +# that was provided so /usr/sbin/syslogd becomes plain 'syslogd' after +# basename ran) +# + + base=$(/usr/bin/basename $1) +# +# the pidlist variable will contains the output of the pidof command. +# pidof will try to find the PID's that belong to a certain string; +# $base in this case +# + + pidlist=$(/bin/pidof -o $$ -o $PPID -o %PPID -x $base) + + pid="" + + for apid in $pidlist + do + if [ -d /proc/$apid ] + then + pid="$pid $apid" + fi + done +# +# If the $pid variable contains anything (from the previous for loop) it +# means the daemon is already running +# + + if [ ! -n "$pid" ] + then +# +# Empty $pid variable means it's not running, so we run $* (all +# parameters giving to this function from the script) and then check the +# return value +# + $* + evaluate_retval + else +# +# The variable $pid was not empty, meaning it was already running. We +# print [FAILED] now +# + print_status failure + fi + +} + +# +# The killproc function kills a process with proper error checking +# + +killproc() +{ + +# +# If no parameters are given to the print_status function, print usage +# information. + +# + + if [ $# = 0 ] + then + echo "Usage: killproc {program} [signal]" + exit 1 + fi + +# +# Find the basename of the first parameter (the daemon's name without +# the path +# that was provided so /usr/sbin/syslogd becomes plain 'syslogd' after +# basename ran) +# + + base=$(/usr/bin/basename $1) + +# +# Check if we gave a signal to kill the process with (like -HUP, -TERM, +# -KILL, etc) to this function (the second parameter). If no second +# parameter was provided set the nolevel variable. Else set the +# killlevel variable to the value of $2 (the second parameter) +# + + if [ "$2" != "" ] + then + killlevel=-$2 + else + nolevel=1 + fi + +# +# the pidlist variable will contains the output of the pidof command. +# pidof will try to find the PID's that belong to a certain string; +# $base in this case + + pidlist=$(/bin/pidof -o $$ -o $PPID -o %PPID -x $base) + + pid="" + + for apid in $pidlist + do + if [ -d /proc/$apid ] + then + pid="$pid $apid" + fi + done + +# +# If $pid contains something from the previous for loop it means one or + +# more PID's were found that belongs to the processes to be killed +# + if [ -n "$pid" ] + then +# +# If no kill level was specified we'll try -TERM first and then sleep +# for 2 seconds to allow the kill to be completed +# + if [ "$nolevel" = 1 ] + then + /bin/kill -TERM $pid +/usr/bin/sleep 2 +# +# If after -TERM the PID still exists we'll try killing it with -KILL +# and wait for 2 seconds again to allow the kill to be completed +# + + if ps h $pid >/dev/null 2>&1 + then + /bin/kill -KILL $pid +/usr/bin/sleep 2 + fi + /bin/ps h $pid >/dev/null 2>&1 + if [ $? = 0 ] + then +# +# If after the -KILL it still exists it can't be killed for some reason +# and we'll print [FAILED] +# + print_status failure + else +# +# It was killed, remove possible stale PID file in /var/run and +# print [ OK ] +# + /bin/rm -f /var/run/$base.pid + print_status success + fi + else +# +# A kill level was provided. Kill with the provided kill level and wait +# for 2 seconds to allow the kill to be completed + +# + /bin/kill $killlevel $pid +/usr/bin/sleep 2 + /bin/ps h $pid >/dev/null 2>&1 + if [ $? = 0 ] + then +# +# If ps' return value is 0 it means it ran ok which indicates that the +# PID still exists. This means the process wasn't killed properly with +# the signal provided. Print [FAILED] +# + print_status failure + else +# +# If the return value was 1 or higher it means the PID didn't exist +# anymore which means it was killed successfully. Remove possible stale +# PID file and print [ OK ] +# + /bin/rm -f /var/run/$base.pid + print_status success + fi + fi + else +# +# The PID didn't exist so we can't attempt to kill it. Print [FAILED] +# + print_status failure + fi +} + +# +# The reloadproc functions sends a signal to a daemon telling it to +# reload it's configuration file. This is almost identical to the +# killproc function with the exception that it won't try to kill it with +# a -KILL signal (aka -9) +# + +reloadproc() +{ + +# +# If no parameters are given to the print_status function, print usage +# information. + +# + + if [ $# = 0 ] + then + echo "Usage: reloadproc {program} [signal]" + exit 1 + fi + +# +# Find the basename of the first parameter (the daemon's name without +# the path +# that was provided so /usr/sbin/syslogd becomes plain 'syslogd' after +# basename ran) +# + + base=$(/usr/bin/basename $1) + +# +# Check if we gave a signal to send to the process (like -HUP) +# to this function (the second parameter). If no second +# parameter was provided set the nolevel variable. Else set the +# killlevel variable to the value of $2 (the second parameter) +# + + + if [ -n "$2" ] + then + killlevel=-$2 + else + nolevel=1 + fi + +# +# the pidlist variable will contains the output of the pidof command. +# pidof will try to find the PID's that belong to a certain string; +# $base in this case + +# + + pidlist=$(/bin/pidof -o $$ -o $PPID -o %PPID -x $base) + + pid="" + + for apid in $pidlist + do + if [ -d /proc/$apid ] + then + pid="$pid $apid" + fi + done + +# +# If $pid contains something from the previous for loop it means one or +# more PID's were found that belongs to the processes to be reloaded +# + + if [ -n "$pid" ] + then + +# +# If nolevel was set we will use the default reload signal SIGHUP. +# + + if [ "$nolevel" = 1 ] + then + /bin/kill -SIGHUP $pid + evaluate_retval + else +# +# Else we will use the provided signal +# + + /bin/kill $killlevel $pid + evaluate_retval + fi + else +# +# If $pid is empty no PID's have been found that belong to the process +# and print [FAILED] +# + + print_status failure + fi +} + +# +# The statusproc function will try to find out if a process is running +# or not +# + +statusproc() +{ + +# +# If no parameters are given to the print_status function, print usage +# information. + +# + + if [ $# = 0 ] + then + echo "Usage: status {program}" + return 1 + fi + +# +# $pid will contain a list of PID's that belong to a process +# + + pid=$(/bin/pidof -o $$ -o $PPID -o %PPID -x $1) + if [ -n "$pid" ] + then +# +# If $pid contains something, the process is running, print the contents +# of the $pid variable +# + echo "$1 running with Process ID $pid" + return 0 + fi + +# +# If $pid doesn't contain it check if a PID file exists and inform the +# user about this stale file. +# + + if [ -f /var/run/$1.pid ] + then + pid=$(/usr/bin/head -1 /var/run/$1.pid) + if [ -n "$pid" ] + then + echo "$1 not running but /var/run/$1.pid exists" + return 1 + fi + else + echo "$1 is not running" + fi + +} + +# End /etc/init.d/functions +<userinput>EOF</userinput> + +</literallayout> + +</sect1> + |