#!/bin/sh
#
# $NetBSD: 02-wedgenames,v 1.6 2021/01/09 16:25:19 mlelstv Exp $
#
# Try to maintain symlinks to wedge devices
#

export LC_ALL=C

event="$1"
shift
devices=$@

wedgedir=/dev/wedges

recurse()
{
	test -d "$1" && ls -1af "$1" \
	| while read n; do
		case $n in
		.|..) ;;
		*)
			echo "$1/$n"
			if [ -L "$1/$n" ]; then
				: #nothing
			elif [ -d "$1/$n" ]; then
				recurse "$1/$n"
			fi
			;;
		esac
	done
}

simple_readlink()
{
	local x

	x=$(test -e "$1" && ls -ld "$1")
	case $x in
	*'-> '*) echo ${x#*-> };;
	esac
}

ordtable=$(
	for n1 in 0 1 2 3 4 5 6 7 8 9 a b c d e f; do
	for n2 in 0 1 2 3 4 5 6 7 8 9 a b c d e f; do
		echo "\$'\x$n1$n2') x=$n1$n2;;"
	done
	done
)

ord()
{
	local x
	eval "case \$1 in $ordtable esac"
	echo -n $x
}

encode()
{
	local a

	a=$1
	while [ -n "$a" ]; do
		c="${a%"${a#?}"}"
		a=${a#?}
		case $c in
		[[:alnum:]._:\;!^$\&~\(\)[\]{}=,+\-/])
			;;
		*)
			c='%%'$(ord "$c")
			;;
		esac
		echo -n "$c"
	done
}

remove_wedge() {
	recurse "$wedgedir" \
	| while read w; do
		t=$(simple_readlink "$w")
		if [ x"$t" = x"/dev/$1" ]; then
			rm -f "$w"
			basedir=${w%/*}
			rmdir -p "$basedir" 2>/dev/null
		fi
	done
}

add_wedge() {
	dkctl "$1" getwedgeinfo \
	| while read l; do
		case $l in
		*': '*)
			n="${l#*: }"
			n=$(encode "$n")
			test -d $wedgedir || mkdir -m 755 $wedgedir
			basedir="$wedgedir/$n"
			basedir=${basedir%/*}
			test -d "$basedir" || mkdir -p -m 755 "$basedir"
			if oldlink=$(simple_readlink "$wedgedir/$n"); then
				if [ x"$oldlink" != x"/dev/$1" ]; then
					rm -f "$wedgedir/$n"
					ln -s "/dev/$1" "$wedgedir/$n"
				fi
			else
				ln -s "/dev/$1" "$wedgedir/$n"
			fi
			;;
		esac
		break
	done
}

for device in $devices; do
	case $device in
	dk*)
		case $event in
		device-attach)
			remove_wedge $device
			add_wedge $device
			;;
		device-detach)
			remove_wedge $device
			;;
		esac
		;;
	esac
done
