CHAPTER 6 Startup and Shutdown
There should be at least one entry in inittab for each run level. The scripts in the /etc/rc#.d directories begin with either the letter K or S. When these scripts are executed by the /sbin/rc# script first the K (kill) files are run, then the S (start) files, to kill and start the various daemons needed for that run level. These scripts have names of the form:
[K,S][0-9][0-9]filename[0-99]
and are executed in ASCII sort order.
To start the daemons the RC scripts check for the existence of the /etc/rc#.d directory, then for any files beginning with "S" in that subdirectory, and then they execute those scripts with the "start" option.
The appropriate lines in the RC file, e.g. those in /sbin/rc2, to start the scripts beginning with "S", are:
if [ -d /etc/rc2.d ]
then
for f in /etc/rc2.d/S*
{
if [ -s ${f} ]
then
case ${f} in
*.sh) . ${f} ;; # source it
*) /sbin/sh ${f} start ;; # sub shell
esac
fi
}
fi
Then in /etc/rc2.d you would have scripts such as the K20lp script and the S80lp script to stop and start, respectively, the lineprinter scheduler. These scripts are actually identical and are run with either the stop or start options to cause the desired effect. Some of the scripts are symbolic links to files in the /etc/init.d directory. The K and S files for a service don't have to be in the same RC directory. You might stop a service when entering run level 2, and start it when entering run level 3.
A typical script might look something like (substitute your daemon name for sample_daemon):
#!/bin/sh
# start up sample_daemon, installed by FGF, 04/12/96
#
case "$1" in
'start')
if [ -x /opt/local/sbin/sample_daemon ]; then
/opt/local/sbin/sample_daemon && echo "Starting sample_daemon ... "
fi
;;
'stop')
pid=`/usr/bin/ps -e | /usr/bin/grep sample_daemon | /usr/bin/sed -e 's/^ *//' -e 's/ .*//'`
if [ "${pid}" != "" ]; then
echo "Stopping sample_daemon "
/usr/bin/kill ${pid}
fi
;;
*)
echo "Usage: /etc/init.d/sample_daemon { start | stop }"
;;
esac
exit 0
To modify the run states you can write your own startup scripts, install scripts in /etc/init.d and make symbolic links to them in the /etc/rc#.d directory (with the proper K,S names), or add entries to /etc/inittab.
Your /etc/inittab file has entries of the form:
id:run-state:action:process
where:
wait start the process and wait for it to terminate
once start the process when entering the run level, but don't wait for it to complete and don't restart it if it dies
boot process the entry only on boot up
bootwait process the first time init moves from single- to multi-user state after a boot and wait for it to complete
powerfail execute when init receives a power-fail signal, SIGPWR
powerwait execute when a power-fail signal is received and wait for it to complete
off send a SIGTERM to the process followed 5 seconds later by a SIGKILL to forcibly terminate it
ondemand same as respawn
initdefault process when init is initially invoked - sets the default run-level to enter
sysinit process this entry before accessing the console and wait for it to complete
The init process first searches /etc/inittab for initdefault entries to determine the run-level. Next, sysinit entries are executed. Following this all process whose run-state matches the initdefault value are executed. Entries are processed starting from the top of the table and working down.
A typical inittab might look similar to:
ap::sysinit:/sbin/autopush -f /etc/iu.ap
fs::sysinit:/sbin/rcS >/dev/console 2>&1 </dev/console
is:3:initdefault:
p3:s1234:powerfail:/sbin/shutdown -y -i0 -g0 >/dev/console 2>&1
s0:0:wait:/sbin/rc0 off >/dev/console 2>&1 </dev/console
s1:1:wait:/sbin/shutdown -y -iS -g0 >/dev/console 2>&1 </dev/console
s2:23:wait:/sbin/rc2 >/dev/console 2>&1 </dev/console
s3:3:wait:/sbin/rc3 >/dev/console 2>&1 </dev/console
s5:5:wait:/sbin/rc5 ask >/dev/console 2>&1 </dev/console
s6:6:wait:/sbin/rc6 reboot >/dev/console 2>&1 </dev/console
of:0:wait:/sbin/uadmin 2 0 >/dev/console 2>&1 </dev/console
fw:5:wait:/sbin/uadmin 2 2 >/dev/console 2>&1 </dev/console
RB:6:wait:/sbin/sh -c 'echo "\nThe system is being restarted."' >/dev/console 2>&1
rb:6:wait:/sbin/uadmin 2 1 >/dev/console 2>&1 </dev/console
sc:234:respawn:/usr/lib/saf/sac -t 300
co:234:respawn:/usr/lib/saf/ttymon -g -h -p "'uname -n' console login: " -T sun -d /dev/console -l
console -m ldterm,ttcompat
To cause init to reread inittab specify q or Q to the init (or telinit) command, e.g.
# init q -or- telinit q
This is similar to doing a "kill -HUP 1" under SunOS 4.X.