Subject: /etc/rc.d/bootconf.sh enhancements
To: None <current-users@netbsd.org>
From: Jukka Salmi <j+nbsd@2006.salmi.ch>
List: current-users
Date: 01/21/2006 13:20:12
--bp/iNruPH9dso1Pn
Content-Type: text/plain; charset=us-ascii
Content-Disposition: inline

Hello,

because not being too happy with the current bootconf.sh rc script I
rewrote it, trying to keep it fully backward compatible to existing
setups. Changes:

* With traditional bootconf.sh, having many configurations is cumbersome
  to setup and maintain. With my bootconf.sh, each configuration may
  have some options. Consider e.g the following seup:

    - configurations: `home', `work' and `away'
    - `home' has options `nonet', `lan' and `wlan'
    - `work' has options `lan', `customer1' and `customer2'
    - `away' has no options

  With the current bootconf.sh, you'd need seven /etc/etc.* directories
  for this setup, instead of just three of them with some additional
  options. These options can then be use in rc.conf like this:

	case "$bootconf_option" in
		lan|wlan)
			sshd=YES
			;;
		nonet)
			inetd=NO
			;;
	esac

* Print countdown timer with user-settable delay. If the countdown
  elapses or enter is hit while it is still running, the default
  configuration is started with the option it was last used with. If
  the countdown is interrupted (Ctrl-C), a (very basic) menu is printed,
  prompting for configuration name and option.


The rewritten bootconf.sh script is attached. To use its new options
feature, add some options to your existing configurations:

$ echo "bootconf_options='opt1 opt2 opt3'" >/etc/etc.conf1/bootconf.options
$ echo "bootconf_options='opt4 opt5 opt6'" >/etc/etc.conf2/bootconf.options
$ [...]

and change the rc.conf files to make use of these options (see above).
Then copy the attached bootconf.options file to /etc and source it in
the rc.conf files, i.e. insert the line `. /etc/bootconf.option' before
you first refer to ${bootconf_option} in rc.conf.

BTW: I put setting used for all configurations to /etc/rc.conf.global,
sourcing this file at the end of all rc.conf files.


Comments are welcome!

Cheers, Jukka

P.S.: a problem I couldn't solve yet: if the countdown timer is killed
before it elapses,

[1]   Terminated             countdown "${con...

is printed to the console on boot-up; I can't reproduce this when
running bootconf.sh manually... Who prints this? The shell? Asked
differently: who prints the `Terminated' line here:

$ sleep 30 >/dev/null 2>&1 &                                                   
[1] 5096
$ kill $! >/dev/null 2>&1                                                      
[1] + Terminated           sleep 30 > /dev/null 2>&1 

TIA...

-- 
bashian roulette:
$ ((RANDOM%6)) || rm -rf ~

--bp/iNruPH9dso1Pn
Content-Type: application/x-sh
Content-Disposition: attachment; filename="bootconf.sh"
Content-Transfer-Encoding: quoted-printable

#!/bin/sh=0A#=0A# $NetBSD$=0A#=0A=0A# PROVIDE: bootconf=0A# REQUIRE: mountc=
ritlocal=0A=0A# Refer to newbtconf(8) for more information.=0A=0Abootconf_s=
tart()=0A{=0A	local def=3D default=3D=0A=0A	if [ ! -e /etc/etc.current ]; t=
hen=0A		return 0=0A	fi=0A	if [ -h /etc/etc.default ]; then=0A		def=3D$(ls -=
ld /etc/etc.default 2>&1)=0A		default=3D"${def##*-> *etc.}"=0A	else=0A		def=
ault=3D'current'=0A	fi=0A	if [ "$default" =3D 'current' ]; then=0A		def=3D$=
(ls -ld /etc/etc.current 2>&1)=0A		default=3D"${def##*-> *etc.}"=0A	fi=0A	c=
onf=3D"$default"=0A=0A	bootconf=0A=0A	case "$conf" in=0A	current|default|"$=
default")=0A		;;=0A	*)=0A		rm -f /etc/etc.current=0A		ln -s /etc/etc."$conf=
" /etc/etc.current=0A		;;=0A	esac=0A=0A	if [ -f /etc/rc.conf ] ; then=0A		.=
 /etc/rc.conf=0A	fi=0A}=0A=0Abootconf()=0A{=0A	local bc_opt=3D bc_opt_str=
=3D=0A	local pid=3D line=3D=0A=0A	bc_opt=3D"$(get_bc_opt)" && bc_opt_str=3D=
", $bc_opt"=0A=0A	echo 'bootconf: Ctrl-C to select configuration, enter for=
 default'=0A	countdown "$conf$bc_opt_str" ${bootconf_delay:-30} &=0A	pid=3D=
$!=0A=0A	# set up self-resetting traps:=0A	#  SIGCHLD: countdown elapsed=0A=
	#  SIGINT:  user typed ^C=0A	trap 'trap - CHLD; echo; return' CHLD=0A	trap=
 "trap - CHLD; trap : INT; kill $pid; select_conf; return" INT=0A=0A	# if t=
his read returns, the user must have hit enter while the=0A	# countdown was=
 running -> reset traps and and kill countdown=0A	read line=0A	trap - CHLD=
=0A	trap : INT=0A	kill $pid=0A=0A	# XXX who prints=0A	# [1]   Terminated   =
          countdown "${con...=0A	# shell? kill? !?$%@#=0A}=0A=0Acountdown()=
=0A{=0A	local bc=3D"$1"=0A	local delay=3D$2=0A	local i=3D$delay=0A=0A	while=
 [ $i -gt 0 ]; do=0A		printf "\rUsing boot-up configuration \`%s' in %*d" \=
=0A		    "$bc" ${#delay} $i=0A		i=3D$(($i-1))=0A		sleep 1=0A	done=0A	printf=
 "\rUsing boot-up configuration \`%s' in %*d" \=0A	    "$bc" ${#delay} 0=0A=
}=0A=0A#=0A# Prompt for boot-up configuration name.=0A# If the chosen confi=
guration has options, i.e. the file=0A# /etc/etc.$conf/bootconf.options set=
s the `bootconf_options' variable to=0A# contain option names, additionally=
 prompt for desired option.=0A#=0Aselect_conf()=0A{=0A	local default=3D"$co=
nf"=0A	local dir=3D name=3D=0A	local bootconf_options=3D bc_opt=3D bc_opt_d=
ef=3D=0A=0A	echo=0A	while : ; do=0A		echo -n 'Boot-up configurations:'=0A		=
for dir in /etc/etc.*; do=0A			name=3D"${dir##/etc/etc.}"=0A			case "$name"=
 in=0A			current|default|\*)=0A				continue=0A				;;	=0A			*)=0A				[ "$nam=
e" =3D "$default" ] && name=3D"[$name]"=0A				echo -n " $name"=0A				;;=0A	=
		esac=0A		done=0A		echo=0A=0A		echo -n "Configuration [$default]: "=0A		re=
ad conf=0A		[ -z "$conf" ] && conf=3D"$default"=0A=0A		if [ ! -d /etc/etc."=
$conf"/. ]; then=0A			echo "Invalid configuration \`$conf'"=0A			conf=3D=0A=
			continue=0A		fi=0A=0A		# if there are no config options, we're done=0A		=
[ -f /etc/etc."$conf"/bootconf.options ] || break=0A		bootconf_options=3D=
=0A		. /etc/etc."$conf"/bootconf.options=0A		[ -z "$bootconf_options" ] && =
break=0A=0A		bc_opt=3D=0A		bc_opt_def=3D"$(get_bc_opt)"=0A=0A		# read until=
 we get a valid option=0A		while :; do=0A			echo -n "Configuration options =
for \`$conf':"=0A			for name in $bootconf_options; do=0A				[ "$name" =3D "=
$bc_opt_def" ] && name=3D"[$name]"=0A				echo -n " $name"=0A			done=0A			ec=
ho=0A=0A			echo -n "Option${bc_opt_def:+ [$bc_opt_def]}: "=0A			read bc_opt=
=0A			[ -z "$bc_opt" ] && bc_opt=3D"$bc_opt_def"=0A=0A			# c: choose differ=
ent configuration=0A			[ "$bc_opt" =3D 'c' ] && break=0A=0A			# check if de=
sired option is valid=0A			for name in $bootconf_options; do=0A				[ "$bc_o=
pt" !=3D "$name" ] && continue=0A				# remember choice=0A				echo "bc_opt=
=3D'$bc_opt'" \=0A				    >/etc/etc."$conf"/.bootconf.option=0A				break 3=
=0A			done=0A			[ -z "$bc_opt" ] || echo "Invalid option \`$bc_opt'"=0A		do=
ne=0A	done=0A=0A	echo "Using boot-up configuration \`$conf${bc_opt:+, $bc_o=
pt}'"=0A}=0A=0Aget_bc_opt()=0A{=0A	local bc_opt=3D=0A=0A	[ -f /etc/etc."$co=
nf"/.bootconf.option ] && \=0A	    . /etc/etc."$conf"/.bootconf.option=0A=
=0A	[ -z "$bc_opt" ] && return 1=0A	echo "$bc_opt"=0A}=0A=0A=0Acase "$1" in=
 *start)=0A	bootconf_start ;;=0Aesac=0A
--bp/iNruPH9dso1Pn
Content-Type: text/plain; charset=us-ascii
Content-Disposition: attachment; filename="bootconf.option"

# /etc/bootconf.option

bc_opt=
[ -f /etc/etc.current/.bootconf.option ] && \
    . /etc/etc.current/.bootconf.option
bootconf_option="$bc_opt"
unset bc_opt

--bp/iNruPH9dso1Pn--