xref: /freebsd/usr.sbin/bsdconfig/share/device.subr (revision fd962ac6997aba7e64007113ed1354e0a88b6e38)
17323adacSDevin Teskeif [ ! "$_DEVICE_SUBR" ]; then _DEVICE_SUBR=1
27323adacSDevin Teske#
37323adacSDevin Teske# Copyright (c) 2012-2013 Devin Teske
47323adacSDevin Teske# All Rights Reserved.
57323adacSDevin Teske#
67323adacSDevin Teske# Redistribution and use in source and binary forms, with or without
77323adacSDevin Teske# modification, are permitted provided that the following conditions
87323adacSDevin Teske# are met:
97323adacSDevin Teske# 1. Redistributions of source code must retain the above copyright
107323adacSDevin Teske#    notice, this list of conditions and the following disclaimer.
117323adacSDevin Teske# 2. Redistributions in binary form must reproduce the above copyright
127323adacSDevin Teske#    notice, this list of conditions and the following disclaimer in the
137323adacSDevin Teske#    documentation and/or other materials provided with the distribution.
147323adacSDevin Teske#
157323adacSDevin Teske# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
167323adacSDevin Teske# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING BUT NOT LIMITED TO, THE
177323adacSDevin Teske# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
187323adacSDevin Teske# ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
197323adacSDevin Teske# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
207323adacSDevin Teske# DAMAGES (INLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
217323adacSDevin Teske# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
227323adacSDevin Teske# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
237323adacSDevin Teske# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
247323adacSDevin Teske# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
257323adacSDevin Teske# SUCH DAMAGE.
267323adacSDevin Teske#
277323adacSDevin Teske# $FreeBSD$
287323adacSDevin Teske#
297323adacSDevin Teske############################################################ INCLUDES
307323adacSDevin Teske
317323adacSDevin TeskeBSDCFG_SHARE="/usr/share/bsdconfig"
327323adacSDevin Teske. $BSDCFG_SHARE/common.subr || exit 1
337323adacSDevin Teskef_dprintf "%s: loading includes..." device.subr
347323adacSDevin Teskef_include $BSDCFG_SHARE/dialog.subr
357323adacSDevin Teskef_include $BSDCFG_SHARE/strings.subr
367323adacSDevin Teskef_include $BSDCFG_SHARE/struct.subr
377323adacSDevin Teske
387323adacSDevin TeskeBSDCFG_LIBE="/usr/libexec/bsdconfig"
397323adacSDevin Teskef_include_lang $BSDCFG_LIBE/include/messages.subr
407323adacSDevin Teske
417323adacSDevin Teske############################################################ GLOBALS
427323adacSDevin Teske
437323adacSDevin TeskeDEVICES=
447323adacSDevin TeskeDEVICE_NAMES=
457323adacSDevin Teske
467323adacSDevin Teske# A "device" from sysinstall's point of view
477323adacSDevin Teskef_struct_define DEVICE \
487323adacSDevin Teske	name		\
497323adacSDevin Teske	desc		\
507323adacSDevin Teske	devname		\
517323adacSDevin Teske	type		\
527323adacSDevin Teske	enabled		\
537323adacSDevin Teske	init		\
547323adacSDevin Teske	get		\
557323adacSDevin Teske	shutdown	\
567323adacSDevin Teske	flags		\
577323adacSDevin Teske	private		\
587323adacSDevin Teske	volume
597323adacSDevin Teske
607323adacSDevin Teske# Network devices have their `private' property set to this
617323adacSDevin Teskef_struct_define DEVICE_INFO \
627323adacSDevin Teske	use_rtsol use_dhcp ipaddr ipv6addr netmask extras
637323adacSDevin Teske
647323adacSDevin Teskesetvar DEVICE_TYPE_NONE		1
657323adacSDevin Teskesetvar DEVICE_TYPE_DISK		2
667323adacSDevin Teskesetvar DEVICE_TYPE_FLOPPY	3
677323adacSDevin Teskesetvar DEVICE_TYPE_FTP		4
687323adacSDevin Teskesetvar DEVICE_TYPE_NETWORK	5
697323adacSDevin Teskesetvar DEVICE_TYPE_CDROM	6
707323adacSDevin Teskesetvar DEVICE_TYPE_USB		7
717323adacSDevin Teskesetvar DEVICE_TYPE_DOS		8
727323adacSDevin Teskesetvar DEVICE_TYPE_UFS		9
737323adacSDevin Teskesetvar DEVICE_TYPE_NFS		10
747323adacSDevin Teskesetvar DEVICE_TYPE_ANY		11
757323adacSDevin Teskesetvar DEVICE_TYPE_HTTP_PROXY	12
767323adacSDevin Teske
777323adacSDevin Teske#
787323adacSDevin Teske# Default behavior is to call f_device_get_all() automatically when loaded.
797323adacSDevin Teske#
807323adacSDevin Teske: ${DEVICE_SELF_SCAN_ALL=1}
817323adacSDevin Teske
827323adacSDevin Teske############################################################ FUNCTIONS
837323adacSDevin Teske
847323adacSDevin Teske# f_device_try $name [$i [$var_path]]
857323adacSDevin Teske#
867323adacSDevin Teske# Test a particular device. If $i is given, then $name is expected to contain a
877323adacSDevin Teske# single "%d" where $i will be inserted using printf. If $var_path is given,
887323adacSDevin Teske# it is used as a variable name to provide the caller the device pathname.
897323adacSDevin Teske#
907323adacSDevin Teske# Returns success if the device path exists and is a cdev.
917323adacSDevin Teske#
927323adacSDevin Teskef_device_try()
937323adacSDevin Teske{
947323adacSDevin Teske	local name="$1" i="$2" var_path="$3" unit
957323adacSDevin Teske	if [ "$i" ]; then
967323adacSDevin Teske		unit=$( printf "$name" "$i" )
977323adacSDevin Teske	else
987323adacSDevin Teske		unit="$name"
997323adacSDevin Teske	fi
1007323adacSDevin Teske	case "$unit" in
1017323adacSDevin Teske	/dev/*) : good ;; # already qualified
1027323adacSDevin Teske	*) unit="/dev/$unit" ;;
1037323adacSDevin Teske	esac
1047323adacSDevin Teske	[ "$var_path" ] && setvar "$var_path" "$unit"
1057323adacSDevin Teske	f_dprintf "f_device_try: making sure %s is a device node" "$unit"
1067323adacSDevin Teske	if [ -c "$unit" ]; then
1077323adacSDevin Teske		f_dprintf "f_device_try: %s is a cdev [good]" "$unit"
1087323adacSDevin Teske		return $SUCCESS
1097323adacSDevin Teske	else
1107323adacSDevin Teske		f_dprintf "f_device_try: %s is not a cdev [skip]" "$unit"
1117323adacSDevin Teske		return $FAILURE
1127323adacSDevin Teske	fi
1137323adacSDevin Teske}
1147323adacSDevin Teske
1157323adacSDevin Teske# f_device_register $name $desc $devname $type $enabled $init_function \
1167323adacSDevin Teske#                   $get_function $shutdown_function $private
1177323adacSDevin Teske#
1187323adacSDevin Teske# Register a device. A `structure' (see struct.subr) is created with the name
1197323adacSDevin Teske# device_$name (so make sure $name contains only alpha-numeric characters or
1207323adacSDevin Teske# the underscore, `_'). The remaining arguments after $name correspond to the
1217323adacSDevin Teske# properties of the `DEVICE' structure-type (defined above).
1227323adacSDevin Teske#
1237323adacSDevin Teske# If not already registered, the device is then appended to the DEVICES
1247323adacSDevin Teske# environment variable, a space-separated list of all registered devices.
1257323adacSDevin Teske#
1267323adacSDevin Teskef_device_register()
1277323adacSDevin Teske{
1287323adacSDevin Teske	local name="$1" desc="$2" devname="$3" type="$4" enabled="$5"
1297323adacSDevin Teske	local init_func="$6" get_func="$7" shutdown_func="$8" private="$9"
1307323adacSDevin Teske
1317323adacSDevin Teske	f_struct_new DEVICE "device_$name" || return $FAILURE
1327323adacSDevin Teske	device_$name set name     "$name"
1337323adacSDevin Teske	device_$name set desc     "$desc"
1347323adacSDevin Teske	device_$name set devname  "$devname"
1357323adacSDevin Teske	device_$name set type     "$type"
1367323adacSDevin Teske	device_$name set enabled  "$enabled"
1377323adacSDevin Teske	device_$name set init     "$init_func"
1387323adacSDevin Teske	device_$name set get      "$get_func"
1397323adacSDevin Teske	device_$name set shutdown "$shutdown_func"
1407323adacSDevin Teske	device_$name set private  "$private"
1417323adacSDevin Teske
1427323adacSDevin Teske	# Scan our global register to see if it needs ammending
1437323adacSDevin Teske	local dev found=
1447323adacSDevin Teske	for dev in $DEVICES; do
1457323adacSDevin Teske		[ "$dev" = "$name" ] || continue
1467323adacSDevin Teske		found=1 && break
1477323adacSDevin Teske	done
1487323adacSDevin Teske	[ "$found" ] || DEVICES="$DEVICES $name"
1497323adacSDevin Teske
1507323adacSDevin Teske	return $SUCCESS
1517323adacSDevin Teske}
1527323adacSDevin Teske
1537323adacSDevin Teske# f_device_reset
1547323adacSDevin Teske#
1557323adacSDevin Teske# Reset the registered device chain.
1567323adacSDevin Teske#
1577323adacSDevin Teskef_device_reset()
1587323adacSDevin Teske{
1597323adacSDevin Teske	local dev
1607323adacSDevin Teske	for dev in $DEVICES; do
1617323adacSDevin Teske		f_device_shutdown $dev
1627323adacSDevin Teske
1637323adacSDevin Teske		#
1647323adacSDevin Teske		# XXX this potentially leaks $dev->private if it's being
1657323adacSDevin Teske		# used to point to something dynamic, but you're not supposed
1667323adacSDevin Teske		# to call this routine at such times that some open instance
1677323adacSDevin Teske		# has its private member pointing somewhere anyway. XXX
1687323adacSDevin Teske		#
1697323adacSDevin Teske		f_struct_free device_$dev
1707323adacSDevin Teske	done
1717323adacSDevin Teske	DEVICES=
1727323adacSDevin Teske}
1737323adacSDevin Teske
1747323adacSDevin Teske# f_device_get_all
1757323adacSDevin Teske#
1767323adacSDevin Teske# Get all device information for devices we have attached.
1777323adacSDevin Teske#
1787323adacSDevin Teskef_device_get_all()
1797323adacSDevin Teske{
1807323adacSDevin Teske	local devname desc
1817323adacSDevin Teske
1827323adacSDevin Teske	f_dprintf "f_device_get_all: Probing devices..."
1837323adacSDevin Teske	f_dialog_info "$msg_probing_devices_please_wait_this_can_take_a_while"
1847323adacSDevin Teske
1857323adacSDevin Teske	# First go for the network interfaces
1867323adacSDevin Teske	for devname in $( ifconfig -l ); do
1877323adacSDevin Teske		# Eliminate network devices that don't make sense
1887323adacSDevin Teske		case "$devname" in
1897323adacSDevin Teske		lo*) continue ;;
1907323adacSDevin Teske		esac
1917323adacSDevin Teske
1927323adacSDevin Teske		# Try and find its description
1937323adacSDevin Teske		f_device_desc "$devname" $DEVICE_TYPE_NETWORK desc
1947323adacSDevin Teske
1957323adacSDevin Teske		f_dprintf "Found a network device named %s" "$devname"
1967323adacSDevin Teske		f_device_register $devname \
1977323adacSDevin Teske			"$desc" "$devname" $DEVICE_TYPE_NETWORK 1 \
1987323adacSDevin Teske			f_media_init_network "" f_media_shutdown_network ""
1997323adacSDevin Teske	done
2007323adacSDevin Teske
2017323adacSDevin Teske	# Next, try to find all the types of devices one might use
2027323adacSDevin Teske	# as a media source for content
2037323adacSDevin Teske	#
2047323adacSDevin Teske
2057323adacSDevin Teske	local dev desc type max n=0
2067323adacSDevin Teske	for dev in $DEVICE_NAMES; do
2077323adacSDevin Teske		n=$(( $n + 1 ))
2087323adacSDevin Teske		# Get the desc, type, and max (with debugging disabled)
2097323adacSDevin Teske		# NOTE: Bypassing f_device_name_get() for efficiency
2107323adacSDevin Teske		debug= f_getvar _device_desc$n desc
2117323adacSDevin Teske		debug= f_getvar _device_type$n type
2127323adacSDevin Teske		debug= f_getvar _device_max$n max
2137323adacSDevin Teske
2147323adacSDevin Teske		local k=0
2157323adacSDevin Teske		while [ $k -lt ${max:-0} ]; do
2167323adacSDevin Teske			i=$k k=$(( $k + 1 ))
2177323adacSDevin Teske			devname=""
2187323adacSDevin Teske			case "$type" in
2197323adacSDevin Teske			$DEVICE_TYPE_CDROM)
2207323adacSDevin Teske				f_device_try "$dev" "$i" devname || continue
2217323adacSDevin Teske				f_device_register "${devname##*/}" "$desc" \
2227323adacSDevin Teske					"$devname" $DEVICE_TYPE_CDROM 1 \
2237323adacSDevin Teske					f_media_init_cdrom f_media_get_cdrom \
2247323adacSDevin Teske					f_media_shutdown_cdrom ""
2257323adacSDevin Teske				f_dprintf "Found a CDROM device for %s" \
2267323adacSDevin Teske				          "$devname"
2277323adacSDevin Teske				;;
2287323adacSDevin Teske			$DEVICE_TYPE_FLOPPY)
2297323adacSDevin Teske				f_device_try "$dev" "$i" devname || continue
2307323adacSDevin Teske				f_device_register "${devname##*/}" "$desc" \
2317323adacSDevin Teske					"$devname" $DEVICE_TYPE_FLOPPY 1 \
2327323adacSDevin Teske					f_media_init_floppy \
2337323adacSDevin Teske					f_media_get_floppy \
2347323adacSDevin Teske					f_media_shutdown_floppy ""
2357323adacSDevin Teske				f_dprintf "Found a floppy device for %s" \
2367323adacSDevin Teske				          "$devname"
2377323adacSDevin Teske				;;
2387323adacSDevin Teske			$DEVICE_TYPE_USB)
2397323adacSDevin Teske				f_device_try "$dev" "$i" devname || continue
2407323adacSDevin Teske				f_device_register "${devname##*/}" "$desc" \
2417323adacSDevin Teske					"$devname" $DEVICE_TYPE_USB 1 \
2427323adacSDevin Teske					f_media_init_usb f_media_get_usb \
2437323adacSDevin Teske					f_media_shutdown_usb ""
2447323adacSDevin Teske				f_dprintf "Found a USB disk for %s" "$devname"
2457323adacSDevin Teske				;;
2467323adacSDevin Teske			esac
2477323adacSDevin Teske		done
2487323adacSDevin Teske	done
2497323adacSDevin Teske
2507323adacSDevin Teske	# Register ISO9660 providers as CDROM devices
2517323adacSDevin Teske	for devname in /dev/iso9660/*; do
2527323adacSDevin Teske		f_device_try "$devname" || continue
2537323adacSDevin Teske		f_device_register "${devname##*/}" "ISO9660 file system" \
2547323adacSDevin Teske			"$devname" $DEVICE_TYPE_CDROM 1 \
2557323adacSDevin Teske			f_media_init_cdrom f_media_get_cdrom \
2567323adacSDevin Teske			f_media_shutdown_cdrom ""
2577323adacSDevin Teske		f_dprintf "Found a CDROM device for %s" "$devname"
2587323adacSDevin Teske	done
2597323adacSDevin Teske
2607323adacSDevin Teske	# Scan for mdconfig(8)-created md(4) devices
2617323adacSDevin Teske	local filename
2627323adacSDevin Teske	for devname in /dev/md[0-9] /dev/md[0-9][0-9]; do
2637323adacSDevin Teske		f_device_try "$devname" || continue
2647323adacSDevin Teske
2657323adacSDevin Teske		# See if the md(4) device is a vnode type backed by a file
2667323adacSDevin Teske		filename=$( sysctl kern.geom.conftxt |
2677323adacSDevin Teske			awk -v devname="${devname##*/}" \
2687323adacSDevin Teske			'
2697323adacSDevin Teske				( $2 == "MD" ) && \
2707323adacSDevin Teske				( $3 == devname ) && \
2717323adacSDevin Teske				( $(NF-2) == "vnode" ) && \
2727323adacSDevin Teske				( $(NF-1) == "file" ) \
2737323adacSDevin Teske				{
2747323adacSDevin Teske					print $NF
2757323adacSDevin Teske				}
2767323adacSDevin Teske			' )
2777323adacSDevin Teske		case "$filename" in
2787323adacSDevin Teske		*.iso) # Register the device as an ISO9660 provider
2797323adacSDevin Teske			f_device_register "${devname##*/}" \
2807323adacSDevin Teske				"md(4) vnode file system" \
2817323adacSDevin Teske				"$devname" $DEVICE_TYPE_CDROM 1 \
2827323adacSDevin Teske				f_media_init_cdrom f_media_get_cdrom \
2837323adacSDevin Teske				f_media_shutdown_cdrom ""
2847323adacSDevin Teske			f_dprintf "Found a CDROM device for %s" "$devname"
2857323adacSDevin Teske			;;
2867323adacSDevin Teske		esac
2877323adacSDevin Teske	done
2887323adacSDevin Teske
2897323adacSDevin Teske	# Finally go get the disks and look for partitions to register
2907323adacSDevin Teske	local diskname slices index type rest slice part
2917323adacSDevin Teske	for diskname in $( sysctl -n kern.disks ); do
2927323adacSDevin Teske
2937323adacSDevin Teske		case "$diskname" in
2947323adacSDevin Teske		cd*)
2957323adacSDevin Teske			# XXX
2967323adacSDevin Teske			#  Due to unknown reasons, kern.disks returns SCSI
2977323adacSDevin Teske			# CDROM as a valid disk. This will prevent bsdconfig
2987323adacSDevin Teske			# from presenting SCSI CDROMs as available disks in
2997323adacSDevin Teske			# various menus. Why GEOM treats SCSI CDROM as a disk
3007323adacSDevin Teske			# is beyond me and that should be investigated.
3017323adacSDevin Teske			# For temporary workaround, ignore SCSI CDROM device.
3027323adacSDevin Teske			#
3037323adacSDevin Teske			continue ;;
3047323adacSDevin Teske		esac
3057323adacSDevin Teske
3067323adacSDevin Teske		# Try to create a list of partitions and their types,
3077323adacSDevin Teske		# consisting of "N,typeN ..." (e.g., "1,0xa5 2,0x06").
3087323adacSDevin Teske		if ! slices=$( fdisk -p "$diskname" 2> /dev/null |
3097323adacSDevin Teske			awk '( $1 == "p" ) { print $2","$3 }' )
3107323adacSDevin Teske		then
3117323adacSDevin Teske			f_dprintf "Unable to open disk %s" "$diskname"
3127323adacSDevin Teske			continue
3137323adacSDevin Teske		fi
3147323adacSDevin Teske
3157323adacSDevin Teske		f_device_register "$diskname" "" \
3167323adacSDevin Teske		                  "/dev/$diskname" $DEVICE_TYPE_DISK 0
3177323adacSDevin Teske		f_dprintf "Found a disk device named %s" "$diskname"
3187323adacSDevin Teske
3197323adacSDevin Teske		# Look for existing partitions to register
3207323adacSDevin Teske		for slice in $slices; do
3217323adacSDevin Teske			index="${slice%%,*}" type="${slice#*,}"
3227323adacSDevin Teske			slice=${diskname}s$index
3237323adacSDevin Teske			case "$type" in
3247323adacSDevin Teske			0x01|0x04|0x06|0x0b|0x0c|0x0e|0xef)
3257323adacSDevin Teske				# DOS partitions to add as "DOS media devices"
3267323adacSDevin Teske				f_device_register "$slice" "" \
3277323adacSDevin Teske					"/dev/$slice" $DEVICE_TYPE_DOS 1 \
3287323adacSDevin Teske					f_media_init_dos f_media_get_dos \
3297323adacSDevin Teske					f_media_shutdown_dos ""
3307323adacSDevin Teske				f_dprintf "Found a DOS partition %s" "$slice"
3317323adacSDevin Teske				;;
3327323adacSDevin Teske			0xa5) # FreeBSD partition
3337323adacSDevin Teske				for part in $(
3347323adacSDevin Teske					bsdlabel -r $slice 2> /dev/null |
3357323adacSDevin Teske						awk -v slice="$slice" '
3367323adacSDevin Teske						( $1 ~ /[abdefgh]:/ ) {
3377323adacSDevin Teske							printf "%s%s\n",
3387323adacSDevin Teske							       slice,
3397323adacSDevin Teske							       substr($1,1,1)
3407323adacSDevin Teske						}'
3417323adacSDevin Teske				); do
3427323adacSDevin Teske					f_quietly dumpfs -m /dev/$part ||
3437323adacSDevin Teske						continue
3447323adacSDevin Teske					f_device_register \
3457323adacSDevin Teske						"$part" "" "/dev/$part" \
3467323adacSDevin Teske						$DEVICE_TYPE_UFS 1 \
3477323adacSDevin Teske						f_media_init_ufs \
3487323adacSDevin Teske						f_media_get_ufs \
3497323adacSDevin Teske						f_media_shutdown_ufs ""
3507323adacSDevin Teske					f_dprintf "Found a UFS partition %s" \
3517323adacSDevin Teske					          "$part"
3527323adacSDevin Teske				done # parts
3537323adacSDevin Teske				;;
3547323adacSDevin Teske			esac
3557323adacSDevin Teske		done # slices
3567323adacSDevin Teske
3577323adacSDevin Teske	done # disks
3587323adacSDevin Teske}
3597323adacSDevin Teske
3607323adacSDevin Teske# f_device_name_get $type $name type|desc|max [$var_to_set]
3617323adacSDevin Teske#
3627323adacSDevin Teske# Fetch the device type (type), description (desc), or maximum number of
3637323adacSDevin Teske# devices to scan for (max) associated with device $name and $type. If $type is
3647323adacSDevin Teske# either NULL, missing, or set to $DEVICE_TYPE_ANY then only $name is used.
3657323adacSDevin Teske# Returns success if a match was found, otherwise failure.
3667323adacSDevin Teske#
3677323adacSDevin Teske# If $var_to_set is missing or NULL, the device name is printed to standard out
3687323adacSDevin Teske# for capturing in a sub-shell (which is less-recommended because of
3697323adacSDevin Teske# performance degredation; for example, when called in a loop).
3707323adacSDevin Teske#
3717323adacSDevin Teskef_device_name_get()
3727323adacSDevin Teske{
3737323adacSDevin Teske	local __type="$1" __name="$2" __prop="$3" __var_to_set="$4"
3747323adacSDevin Teske	local __dev __devtype __n=0
3757323adacSDevin Teske
3767323adacSDevin Teske	# Return failure if no $name or $prop is an unknown property
3777323adacSDevin Teske	[ "$__name" ] || return $FAILURE
3787323adacSDevin Teske	case "$__prop" in type|desc|max) : good ;;
3797323adacSDevin Teske	*) return $FAILURE; esac
3807323adacSDevin Teske
3817323adacSDevin Teske	[ "$__type" = "$DEVICE_TYPE_ANY" ] && __type=
3827323adacSDevin Teske	for __dev in $DEVICE_NAMES; do
3837323adacSDevin Teske		__n=$(( $__n + 1 ))
3847323adacSDevin Teske		[ "$__dev" = "$__name" ] || continue
3857323adacSDevin Teske		f_getvar _device_type$__n __devtype
3867323adacSDevin Teske		[ "${__type:-$__devtype}" = "$__devtype" ] || continue
3877323adacSDevin Teske		f_getvar _device_$__prop$__n $__var_to_set
3887323adacSDevin Teske		return $?
3897323adacSDevin Teske	done
3907323adacSDevin Teske	return $FAILURE
3917323adacSDevin Teske}
3927323adacSDevin Teske
3937323adacSDevin Teske# f_device_name_set $type $name $desc [$max]
3947323adacSDevin Teske#
3957323adacSDevin Teske# Store a description (desc) and [optionally] maximum number of devices to scan
39633a14d6fSDevin Teske# for (max) in-association with device $type and $name. Returns success unless
39733a14d6fSDevin Teske# $name is NULL or missing. Use the f_device_name_get() routine with the same
39833a14d6fSDevin Teske# $name and optionally $type to retrieve one of type, desc, or max properties.
3997323adacSDevin Teske#
4007323adacSDevin Teskef_device_name_set()
4017323adacSDevin Teske{
4027323adacSDevin Teske	local type="$1" name="$2" desc="$3" max="$4"
4037323adacSDevin Teske	local dev devtype n=0 found=
4047323adacSDevin Teske	[ "$name" ] || return $FAILURE
4057323adacSDevin Teske	for dev in $DEVICE_NAMES; do
4067323adacSDevin Teske		n=$(( $n + 1 ))
4077323adacSDevin Teske		[ "$dev" = "$name" ] || continue
4087323adacSDevin Teske		if f_getvar _device_type$n devtype; then
4097323adacSDevin Teske			# Allow multiple entries with same name but diff type
4107323adacSDevin Teske			[ "$devtype" = "$type" ] || continue
4117323adacSDevin Teske		fi
4127323adacSDevin Teske		found=1 && break
4137323adacSDevin Teske	done
4147323adacSDevin Teske	if [ ! "$found" ]; then
4157323adacSDevin Teske		DEVICE_NAMES="$DEVICE_NAMES $name"
4167323adacSDevin Teske		n=$(( $n + 1 ))
4177323adacSDevin Teske	fi
4187323adacSDevin Teske	setvar _device_type$n "$type"
4197323adacSDevin Teske	setvar _device_desc$n "$desc"
4207323adacSDevin Teske	[ "${4+set}" ] && setvar _device_max$n "$max"
4217323adacSDevin Teske	return $SUCCESS
4227323adacSDevin Teske}
4237323adacSDevin Teske
4247323adacSDevin Teske# f_device_desc $device_name $device_type [$var_to_set]
4257323adacSDevin Teske#
4267323adacSDevin Teske# Print a description for a device name (eg., `fxp0') given a specific device
4277323adacSDevin Teske# type/class.
4287323adacSDevin Teske#
4297323adacSDevin Teske# If $var_to_set is missing or NULL, the device description is printed to
4307323adacSDevin Teske# standard out for capturing in a sub-shell (which is less-recommended because
4317323adacSDevin Teske# of performance degredation; for example, when called in a loop).
4327323adacSDevin Teske#
4337323adacSDevin Teskef_device_desc()
4347323adacSDevin Teske{
4357323adacSDevin Teske	local __name="$1" __type="$2" __var_to_set="$3"
4367323adacSDevin Teske	local __devname __devunit __cp
4377323adacSDevin Teske
4387323adacSDevin Teske	# Check variables
4397323adacSDevin Teske	[ "$__name" ] || return $SUCCESS
4407323adacSDevin Teske	[ "$__type" = "$DEVICE_TYPE_ANY" ] && type=
4417323adacSDevin Teske	[ "$__var_to_set" ] && { setvar "$__var_to_set" "" || return; }
4427323adacSDevin Teske
4437323adacSDevin Teske	#
4447323adacSDevin Teske	# Return sysctl MIB dev.NAME.UNIT.%desc if it exists,
4457323adacSDevin Teske	# otherwise fall through to below static list.
4467323adacSDevin Teske	#
4477323adacSDevin Teske	if f_have sysctl; then
4487323adacSDevin Teske		__devname="${__name%%[0-9]*}"
4497323adacSDevin Teske		__devunit="${__name#$__devname}"
4507323adacSDevin Teske		__devunit="${__devunit%%[!0-9]*}"
4517323adacSDevin Teske		if [ "$__var_to_set" ]; then
4527323adacSDevin Teske			if __cp=$(
4537323adacSDevin Teske				sysctl -n "dev.$__devname.$__devunit.%desc" \
4547323adacSDevin Teske				2> /dev/null
4557323adacSDevin Teske			); then
4567323adacSDevin Teske				setvar "$__var_to_set" "$__cp" &&
4577323adacSDevin Teske					return $SUCCESS
4587323adacSDevin Teske			fi
4597323adacSDevin Teske		else
4607323adacSDevin Teske			sysctl -n "dev.$__devname.$__devunit.%desc" \
4617323adacSDevin Teske				2> /dev/null && return $SUCCESS
4627323adacSDevin Teske		fi
4637323adacSDevin Teske	fi
4647323adacSDevin Teske
4657323adacSDevin Teske	local __dev __devtype __n=0
4667323adacSDevin Teske	for __dev in $DEVICE_NAMES; do
4677323adacSDevin Teske		__n=$(( $__n + 1 ))
4687323adacSDevin Teske		debug= f_getvar _device_type$__n __devtype
4697323adacSDevin Teske		[ "${__type:-$__devtype}" = "$__devtype" ] || continue
4707323adacSDevin Teske		if [ "$__devtype" = "$DEVICE_TYPE_NETWORK" ]; then
4717323adacSDevin Teske			__devname=$( f_substr "$__name" 0 ${#__dev} )
4727323adacSDevin Teske			[ "$__devname" = "$__dev" ] || continue
4737323adacSDevin Teske		else
4747323adacSDevin Teske			__devname="${__name%%[0-9]*}"
4757323adacSDevin Teske			__devunit="${__name#$__devname}"
4767323adacSDevin Teske			__devunit="${__devunit%%[!0-9]*}"
4777323adacSDevin Teske			__devname=$( printf "$__dev" $__devunit )
4787323adacSDevin Teske			[ "$__devname" = "$__name" ] || continue
4797323adacSDevin Teske		fi
4807323adacSDevin Teske		debug= f_getvar _device_desc$__n $__var_to_set
4817323adacSDevin Teske		return $?
4827323adacSDevin Teske	done
4837323adacSDevin Teske
4847323adacSDevin Teske	#
4857323adacSDevin Teske	# Sensible fall-backs for specific types
4867323adacSDevin Teske	#
4877323adacSDevin Teske	case "$__type" in
4887323adacSDevin Teske	$DEVICE_TYPE_CDROM)   __cp="<unknown cdrom device type>";;
4897323adacSDevin Teske	$DEVICE_TYPE_DISK)    __cp="<unknown disk device type>";;
4907323adacSDevin Teske	$DEVICE_TYPE_FLOPPY)  __cp="<unknown floppy device type>";;
4917323adacSDevin Teske	$DEVICE_TYPE_USB)     __cp="<unknown usb storage device type>";;
4927323adacSDevin Teske	$DEVICE_TYPE_NETWORK) __cp="<unknown network interface type>";;
4937323adacSDevin Teske	*)
4947323adacSDevin Teske		__cp="<unknown device type>"
4957323adacSDevin Teske	esac
4967323adacSDevin Teske
4977323adacSDevin Teske	if [ "$__var_to_set" ]; then
4987323adacSDevin Teske		setvar "$__var_to_set" "$__cp"
4997323adacSDevin Teske	else
5007323adacSDevin Teske		echo "$__cp"
5017323adacSDevin Teske	fi
5027323adacSDevin Teske
5037323adacSDevin Teske	return $FAILURE
5047323adacSDevin Teske}
5057323adacSDevin Teske
5067323adacSDevin Teske# f_device_rescan
5077323adacSDevin Teske#
5087323adacSDevin Teske# Rescan all devices, after closing previous set - convenience function.
5097323adacSDevin Teske#
5107323adacSDevin Teskef_device_rescan()
5117323adacSDevin Teske{
5127323adacSDevin Teske	f_device_reset
5137323adacSDevin Teske	f_device_get_all
5147323adacSDevin Teske}
5157323adacSDevin Teske
5167323adacSDevin Teske# f_device_find $name [$type [$var_to_set]]
5177323adacSDevin Teske#
5187323adacSDevin Teske# Find one or more registered devices by name, type, or both. Returns a space-
5197323adacSDevin Teske# separated list of devices matching the search criterion.
5207323adacSDevin Teske#
5217323adacSDevin Teske# If $var_to_set is missing or NULL, the device name(s) are printed to standard
5227323adacSDevin Teske# out for capturing in a sub-shell (which is less-recommended because of
5237323adacSDevin Teske# performance degredation; for example, when called in a loop).
5247323adacSDevin Teske#
5257323adacSDevin Teskef_device_find()
5267323adacSDevin Teske{
5277323adacSDevin Teske	local __name="$1" __type="${2:-$DEVICE_TYPE_ANY}" __var_to_set="$3"
5287323adacSDevin Teske	local __dev __devname __devtype __found=
5297323adacSDevin Teske	for __dev in $DEVICES; do
5307323adacSDevin Teske		device_$__dev get name __devname
5317323adacSDevin Teske		device_$__dev get type __devtype
5327323adacSDevin Teske		if [ "$__name" = "$__devname" -o ! "$__name" ] &&
5337323adacSDevin Teske		   [ "$__type" = "$DEVICE_TYPE_ANY" -o \
5347323adacSDevin Teske		     "$__type" = "$__devtype" ]
5357323adacSDevin Teske		then
5367323adacSDevin Teske			__found="$__found $__dev"
5377323adacSDevin Teske		fi
5387323adacSDevin Teske	done
5397323adacSDevin Teske	if [ "$__var_to_set" ]; then
5407323adacSDevin Teske		setvar "$__var_to_set" "${__found# }"
5417323adacSDevin Teske	else
5427323adacSDevin Teske		echo $__found
5437323adacSDevin Teske	fi
5447323adacSDevin Teske	[ "$__found" ] # Return status
5457323adacSDevin Teske}
5467323adacSDevin Teske
5477323adacSDevin Teske# f_device_init $name
5487323adacSDevin Teske#
5497323adacSDevin Teske# Initialize a device by evaluating its `init' function.
5507323adacSDevin Teske#
5517323adacSDevin Teskef_device_init()
5527323adacSDevin Teske{
5537323adacSDevin Teske	local name="$1" init_func
5547323adacSDevin Teske	device_$name get init init_func || return
5557323adacSDevin Teske	${init_func:-:} $name
5567323adacSDevin Teske}
5577323adacSDevin Teske
5587323adacSDevin Teske# f_device_get $name $file [$probe]
5597323adacSDevin Teske#
5607323adacSDevin Teske# Read $file by evaluating the device's `get' function. The file is commonly
5617323adacSDevin Teske# produced on standard output (but it truly depends on the function called).
5627323adacSDevin Teske#
5637323adacSDevin Teskef_device_get()
5647323adacSDevin Teske{
5657323adacSDevin Teske	local name="$1" file="$2" probe="$3" get_func
5667323adacSDevin Teske	device_$name get get get_func || return
5677323adacSDevin Teske	${get_func:-:} $name "$file" ${3+"$probe"}
5687323adacSDevin Teske}
5697323adacSDevin Teske
5707323adacSDevin Teske# f_device_shutdown $name
5717323adacSDevin Teske#
5727323adacSDevin Teske# Shutdown a device by evaluating its `shutdown' function.
5737323adacSDevin Teske#
5747323adacSDevin Teskef_device_shutdown()
5757323adacSDevin Teske{
5767323adacSDevin Teske	local name="$1" shutdown_func
5777323adacSDevin Teske	device_$name get shutdown shutdown_func || return
5787323adacSDevin Teske	${shutdown_func:-:} $name
5797323adacSDevin Teske}
5807323adacSDevin Teske
5817323adacSDevin Teske# f_device_menu $title $prompt $hline $device_type [$helpfile]
5827323adacSDevin Teske#
5837323adacSDevin Teske# Display a menu listing all the devices of a certain type in the system.
5847323adacSDevin Teske#
5857323adacSDevin Teskef_device_menu()
5867323adacSDevin Teske{
5877323adacSDevin Teske	f_dialog_title "$1"
5887323adacSDevin Teske	local title="$DIALOG_TITLE" btitle="$DIALOG_BACKTITLE"
5897323adacSDevin Teske	f_dialog_title_restore
5907323adacSDevin Teske
5917323adacSDevin Teske	local prompt="$2" hline="$3" type="$4" helpfile="$5"
5927323adacSDevin Teske
5937323adacSDevin Teske	local dev devtype devs=
5947323adacSDevin Teske	for dev in $DEVICES; do
5957323adacSDevin Teske		device_$dev get type devtype || continue
5967323adacSDevin Teske		[ "$devtype" = "$type" ] || continue
5977323adacSDevin Teske		devs="$devs $dev"
5987323adacSDevin Teske	done
5997323adacSDevin Teske	[ "$devs" ] || return $FAILURE
6007323adacSDevin Teske
6017323adacSDevin Teske	local sanitize_awk="{ gsub(/'/, \"'\\\\''\"); print }"
6027323adacSDevin Teske
6037323adacSDevin Teske	local desc menu_list=
6047323adacSDevin Teske	for dev in $devs; do
6057323adacSDevin Teske		device_$dev get desc desc
6067323adacSDevin Teske		desc=$( echo "$desc" | awk "$sanitize_awk" )
6077323adacSDevin Teske		menu_list="$menu_list '$dev' '$desc'"
6087323adacSDevin Teske	done
6097323adacSDevin Teske
61074036c4dSDevin Teske	local height width rows
61174036c4dSDevin Teske	eval f_dialog_menu_size height width rows \
6127323adacSDevin Teske	                        \"\$title\"  \
6137323adacSDevin Teske	                        \"\$btitle\" \
6147323adacSDevin Teske	                        \"\$prompt\" \
6157323adacSDevin Teske	                        \"\$hline\"  \
61674036c4dSDevin Teske	                        $menu_list
6177323adacSDevin Teske
6187323adacSDevin Teske	local errexit=
6197323adacSDevin Teske	case $- in *e*) errexit=1; esac
6207323adacSDevin Teske	set +e
6217323adacSDevin Teske
622*fd962ac6SDevin Teske	local mtag
6237323adacSDevin Teske	while :; do
6247323adacSDevin Teske		mtag=$( eval $DIALOG \
6257323adacSDevin Teske			--title \"\$title\"             \
6267323adacSDevin Teske			--backtitle \"\$btitle\"        \
6277323adacSDevin Teske			--ok-label \"\$msg_ok\"         \
6287323adacSDevin Teske			--cancel-label \"\$msg_cancel\" \
6297323adacSDevin Teske			${helpfile:+                    \
6307323adacSDevin Teske			  --help-button                 \
6317323adacSDevin Teske			  --help-label \"\$msg_help\"   \
6327323adacSDevin Teske			  ${USE_XDIALOG:+--help \"\"}   \
6337323adacSDevin Teske			}                               \
63474036c4dSDevin Teske			--menu \"\$prompt\"             \
63574036c4dSDevin Teske			$height $width $rows            \
6367323adacSDevin Teske			$menu_list                      \
6377323adacSDevin Teske			2>&1 >&$DIALOG_TERMINAL_PASSTHRU_FD
6387323adacSDevin Teske		)
6397323adacSDevin Teske		local retval=$?
6407323adacSDevin Teske
6417323adacSDevin Teske		[ $retval -ne 2 ] && break
6427323adacSDevin Teske			# Otherwise, the Help button was pressed
6437323adacSDevin Teske		f_show_help "$helpfile"
64476c853aeSDevin Teske			# ...then loop back to menu
6457323adacSDevin Teske	done
6467323adacSDevin Teske	f_dprintf "retval=%u mtag=[%s]" $retval "$mtag"
6477323adacSDevin Teske
6487323adacSDevin Teske	[ "$errexit" ] && set -e
6497323adacSDevin Teske
650f780b9f5SDevin Teske	if [ $retval -eq 0 ]; then
651f780b9f5SDevin Teske		# Clean up the output of [X]dialog(1) and return it
652*fd962ac6SDevin Teske		f_dialog_data_sanitize mtag
653f780b9f5SDevin Teske		echo "$mtag" >&2
654f780b9f5SDevin Teske	fi
6557323adacSDevin Teske
6567323adacSDevin Teske	return $retval
6577323adacSDevin Teske}
6587323adacSDevin Teske
6597323adacSDevin Teske#
6607323adacSDevin Teske# Short-hand
6617323adacSDevin Teske#
6627323adacSDevin Teskef_cdrom()   {  f_device_name_set $DEVICE_TYPE_CDROM   "$1" "$2" "$3";  }
6637323adacSDevin Teskef_disk()    {  f_device_name_set $DEVICE_TYPE_DISK    "$1" "$2" "$3";  }
6647323adacSDevin Teskef_floppy()  {  f_device_name_set $DEVICE_TYPE_FLOPPY  "$1" "$2" "$3";  }
6657323adacSDevin Teskef_serial()  {  f_device_name_set $DEVICE_TYPE_NETWORK "$1" "$2" "$3";  }
6667323adacSDevin Teskef_usb()     {  f_device_name_set $DEVICE_TYPE_USB     "$1" "$2" "$3";  }
6677323adacSDevin Teskef_network() {  f_device_name_set $DEVICE_TYPE_NETWORK "$1" "$2";       }
6687323adacSDevin Teske
6697323adacSDevin Teske############################################################ MAIN
6707323adacSDevin Teske
6717323adacSDevin Teske# CDROM, Disk, Floppy, Serial, and USB devices/names
6727323adacSDevin Teskef_cdrom  "cd%d"   "SCSI CDROM drive"                  4
6737323adacSDevin Teskef_cdrom  "mcd%d"  "Mitsumi (old model) CDROM drive"   4
6747323adacSDevin Teskef_cdrom  "scd%d"  "Sony CDROM drive - CDU31/33A type" 4
6757323adacSDevin Teskef_disk   "aacd%d" "Adaptec FSA RAID array"            4
676b2963095SAlexander Motinf_disk   "ada%d"  "ATA/SATA disk device"              16
6777323adacSDevin Teskef_disk   "amrd%d" "AMI MegaRAID drive"                4
6787323adacSDevin Teskef_disk   "da%d"   "SCSI disk device"                  16
6797323adacSDevin Teskef_disk   "idad%d" "Compaq RAID array"                 4
6807323adacSDevin Teskef_disk   "ipsd%d" "IBM ServeRAID RAID array"          4
6817323adacSDevin Teskef_disk   "mfid%d" "LSI MegaRAID SAS array"            4
6827323adacSDevin Teskef_disk   "mlxd%d" "Mylex RAID disk"                   4
6837323adacSDevin Teskef_disk   "twed%d" "3ware ATA RAID array"              4
6847323adacSDevin Teskef_floppy "fd%d"   "Floppy Drive unit A"               4
6857323adacSDevin Teskef_serial "cuau%d" "%s on device %s (COM%d)"           16
6867323adacSDevin Teskef_usb    "da%da"  "USB Mass Storage Device"           16
6877323adacSDevin Teske
6887323adacSDevin Teske# Network interfaces/names
6897323adacSDevin Teskef_network "ae"    "Attansic/Atheros L2 Fast Ethernet"
6907323adacSDevin Teskef_network "age"   "Attansic/Atheros L1 Gigabit Ethernet"
6917323adacSDevin Teskef_network "alc"   "Atheros AR8131/AR8132 PCIe Ethernet"
6927323adacSDevin Teskef_network "ale"   "Atheros AR8121/AR8113/AR8114 PCIe Ethernet"
6937323adacSDevin Teskef_network "an"    "Aironet 4500/4800 802.11 wireless adapter"
6947323adacSDevin Teskef_network "ath"   "Atheros IEEE 802.11 wireless adapter"
6957323adacSDevin Teskef_network "aue"   "ADMtek USB Ethernet adapter"
6967323adacSDevin Teskef_network "axe"   "ASIX Electronics USB Ethernet adapter"
6977323adacSDevin Teskef_network "bce"   "Broadcom NetXtreme II Gigabit Ethernet card"
6987323adacSDevin Teskef_network "bfe"   "Broadcom BCM440x PCI Ethernet card"
6997323adacSDevin Teskef_network "bge"   "Broadcom BCM570x PCI Gigabit Ethernet card"
7007323adacSDevin Teskef_network "bm"    "Apple BMAC Built-in Ethernet"
7017323adacSDevin Teskef_network "bwn"   "Broadcom BCM43xx IEEE 802.11 wireless adapter"
7027323adacSDevin Teskef_network "cas"   "Sun Cassini/Cassini+ or NS DP83065 Saturn Ethernet"
7037323adacSDevin Teskef_network "cc3i"  "SDL HSSI sync serial PCI card"
7047323adacSDevin Teskef_network "cue"   "CATC USB Ethernet adapter"
7057323adacSDevin Teskef_network "cxgb"  "Chelsio T3 10Gb Ethernet card"
7067323adacSDevin Teskef_network "dc"    "DEC/Intel 21143 (and clones) PCI Fast Ethernet card"
7077323adacSDevin Teskef_network "de"    "DEC DE435 PCI NIC or other DC21040-AA based card"
7087323adacSDevin Teskef_network "disc"  "Software discard network interface"
7097323adacSDevin Teskef_network "ed"    "Novell NE1000/2000; 3C503; NE2000-compatible PCMCIA"
7107323adacSDevin Teskef_network "el"    "3Com 3C501 Ethernet card"
7117323adacSDevin Teskef_network "em"    "Intel(R) PRO/1000 Ethernet card"
7127323adacSDevin Teskef_network "en"    "Efficient Networks ATM PCI card"
7137323adacSDevin Teskef_network "ep"    "3Com 3C509 Ethernet card/3C589 PCMCIA"
7147323adacSDevin Teskef_network "et"    "Agere ET1310 based PCI Express Gigabit Ethernet card"
7157323adacSDevin Teskef_network "ex"    "Intel EtherExpress Pro/10 Ethernet card"
7167323adacSDevin Teskef_network "fe"    "Fujitsu MB86960A/MB86965A Ethernet card"
7177323adacSDevin Teskef_network "fpa"   "DEC DEFPA PCI FDDI card"
7187323adacSDevin Teskef_network "fwe"   "FireWire Ethernet emulation"
7197323adacSDevin Teskef_network "fwip"  "IP over FireWire"
7207323adacSDevin Teskef_network "fxp"   "Intel EtherExpress Pro/100B PCI Fast Ethernet card"
7217323adacSDevin Teskef_network "gem"   "Apple GMAC or Sun ERI/GEM Ethernet adapter"
7227323adacSDevin Teskef_network "hme"   "Sun HME (Happy Meal Ethernet) Ethernet adapter"
7237323adacSDevin Teskef_network "ie"    "AT&T StarLAN 10 and EN100; 3Com 3C507; NI5210"
7247323adacSDevin Teskef_network "igb"   "Intel(R) PRO/1000 PCI Express Gigabit Ethernet card"
7257323adacSDevin Teskef_network "ipw"   "Intel PRO/Wireless 2100 IEEE 802.11 adapter"
7267323adacSDevin Teskef_network "iwi"   "Intel PRO/Wireless 2200BG/2225BG/2915ABG adapter"
7277323adacSDevin Teskef_network "iwn"   "Intel Wireless WiFi Link 4965AGN IEEE 802.11n adapter"
7287323adacSDevin Teskef_network "ixgbe" "Intel(R) PRO/10Gb Ethernet card"
7297323adacSDevin Teskef_network "ixgb"  "Intel(R) PRO/10Gb Ethernet card"
7307323adacSDevin Teskef_network "ix"    "Intel Etherexpress Ethernet card"
7317323adacSDevin Teske	# Maintain sequential order of above(3): ixgbe ixgb ix
7327323adacSDevin Teskef_network "jme"   "JMicron JMC250 Gigabit/JMC260 Fast Ethernet"
7337323adacSDevin Teskef_network "kue"   "Kawasaki LSI USB Ethernet adapter"
7347323adacSDevin Teskef_network "le"    "AMD Am7900 LANCE or Am79C9xx PCnet Ethernet adapter"
7357323adacSDevin Teskef_network "lge"   "Level 1 LXT1001 Gigabit Ethernet card"
7367323adacSDevin Teskef_network "lnc"   "Lance/PCnet (Isolan/Novell NE2100/NE32-VL) Ethernet"
7377323adacSDevin Teskef_network "lo"    "Loop-back (local) network interface"
7387323adacSDevin Teskef_network "lp"    "Parallel Port IP (PLIP) peer connection"
7397323adacSDevin Teskef_network "malo"  "Marvell Libertas 88W8335 802.11 wireless adapter"
7407323adacSDevin Teskef_network "msk"   "Marvell/SysKonnect Yukon II Gigabit Ethernet"
7417323adacSDevin Teskef_network "mxge"  "Myricom Myri10GE 10Gb Ethernet card"
7427323adacSDevin Teskef_network "nfe"   "NVIDIA nForce MCP Ethernet"
7437323adacSDevin Teskef_network "nge"   "NatSemi PCI Gigabit Ethernet card"
7447323adacSDevin Teskef_network "ng"    "Vimage netgraph(4) bridged Ethernet device"
7457323adacSDevin Teske	# Maintain sequential order of above(2): nge ng
7467323adacSDevin Teskef_network "nve"   "NVIDIA nForce MCP Ethernet"
7477323adacSDevin Teskef_network "nxge"  "Neterion Xframe 10GbE Server/Storage adapter"
7487323adacSDevin Teskef_network "pcn"   "AMD Am79c79x PCI Ethernet card"
7497323adacSDevin Teskef_network "plip"  "Parallel Port IP (PLIP) peer connection"
7507323adacSDevin Teskef_network "ral"   "Ralink Technology IEEE 802.11 wireless adapter"
7517323adacSDevin Teskef_network "ray"   "Raytheon Raylink 802.11 wireless adapter"
7527323adacSDevin Teskef_network "re"    "RealTek 8139C+/8169/8169S/8110S PCI Ethernet adapter"
7537323adacSDevin Teskef_network "rl"    "RealTek 8129/8139 PCI Ethernet card"
7547323adacSDevin Teskef_network "rue"   "RealTek USB Ethernet card"
7557323adacSDevin Teskef_network "rum"   "Ralink Technology USB IEEE 802.11 wireless adapter"
7567323adacSDevin Teskef_network "sf"    "Adaptec AIC-6915 PCI Ethernet card"
7577323adacSDevin Teskef_network "sge"   "Silicon Integrated Systems SiS190/191 Ethernet"
7587323adacSDevin Teskef_network "sis"   "SiS 900/SiS 7016 PCI Ethernet card"
7597323adacSDevin Teskef_network "sk"    "SysKonnect PCI Gigabit Ethernet card"
7607323adacSDevin Teskef_network "snc"   "SONIC Ethernet card"
7617323adacSDevin Teskef_network "sn"    "SMC/Megahertz Ethernet card"
7627323adacSDevin Teske	# Maintain sequential order of above(2): snc sn
7637323adacSDevin Teskef_network "sr"    "SDL T1/E1 sync serial PCI card"
7647323adacSDevin Teskef_network "ste"   "Sundance ST201 PCI Ethernet card"
7657323adacSDevin Teskef_network "stge"  "Sundance/Tamarack TC9021 Gigabit Ethernet"
7667323adacSDevin Teskef_network "ti"    "Alteon Networks PCI Gigabit Ethernet card"
7677323adacSDevin Teskef_network "tl"    "Texas Instruments ThunderLAN PCI Ethernet card"
7687323adacSDevin Teskef_network "txp"   "3Com 3cR990 Ethernet card"
7697323adacSDevin Teskef_network "tx"    "SMC 9432TX Ethernet card"
7707323adacSDevin Teske	# Maintain sequential order of above(2): txp tx
7717323adacSDevin Teskef_network "uath"  "Atheros AR5005UG and AR5005UX USB wireless adapter"
7727323adacSDevin Teskef_network "upgt"  "Conexant/Intersil PrismGT USB wireless adapter"
7737323adacSDevin Teskef_network "ural"  "Ralink Technology RT2500USB 802.11 wireless adapter"
7747323adacSDevin Teskef_network "urtw"  "Realtek 8187L USB wireless adapter"
7757323adacSDevin Teskef_network "vge"   "VIA VT612x PCI Gigabit Ethernet card"
7767323adacSDevin Teskef_network "vlan"  "IEEE 802.1Q VLAN network interface"
7777323adacSDevin Teskef_network "vr"    "VIA VT3043/VT86C100A Rhine PCI Ethernet card"
7787323adacSDevin Teskef_network "vx"    "3COM 3c590 / 3c595 Ethernet card"
7797323adacSDevin Teskef_network "wb"    "Winbond W89C840F PCI Ethernet card"
7807323adacSDevin Teskef_network "wi"    "Lucent WaveLAN/IEEE 802.11 wireless adapter"
7817323adacSDevin Teskef_network "wpi"   "Intel 3945ABG IEEE 802.11 wireless adapter"
7827323adacSDevin Teskef_network "wx"    "Intel Gigabit Ethernet (82452) card"
7837323adacSDevin Teskef_network "xe"    "Xircom/Intel EtherExpress Pro100/16 Ethernet card"
7847323adacSDevin Teskef_network "xl"    "3COM 3c90x / 3c90xB PCI Ethernet card"
7857323adacSDevin Teskef_network "zyd"   "ZyDAS ZD1211/ZD1211B USB 802.11 wireless adapter"
7867323adacSDevin Teske
7877323adacSDevin Teskef_dprintf "%s: Initialized %u known device names/descriptions." device.subr \
7887323adacSDevin Teske	  "$( set -- $DEVICE_NAMES; echo $# )"
7897323adacSDevin Teske
7907323adacSDevin Teske#
7917323adacSDevin Teske# Scan for the above devices unless requeted otherwise
7927323adacSDevin Teske#
7937323adacSDevin Teskef_dprintf "%s: DEVICE_SELF_SCAN_ALL=[%s]" device.subr "$DEVICE_SELF_SCAN_ALL"
7947323adacSDevin Teskecase "$DEVICE_SELF_SCAN_ALL" in
7957323adacSDevin Teske""|0|[Nn][Oo]|[Oo][Ff][Ff]|[Ff][Aa][Ll][Ss][Ee]) : do nothing ;;
7967323adacSDevin Teske*) f_device_get_all
7977323adacSDevin Teskeesac
7987323adacSDevin Teske
7997323adacSDevin Teskef_dprintf "%s: Successfully loaded." device.subr
8007323adacSDevin Teske
8017323adacSDevin Teskefi # ! $_DEVICE_SUBR
802