#!/bin/bash -efu

. shell-error
. shell-signal

handlerdir="/lib/pipeline"
mntdir="/dev/pipeline"

pidfile="/var/run/$PROG.pid"

exit_handler()
{
	local rc="$?"
	trap - EXIT
	rm -f -- "$pidfile"
	exit $rc
}

[ ! -f "$pidfile" ] ||
	fatal "already running"

set_cleanup_handler exit_handler
echo "$$" >"$pidfile"

. /.initrd/initenv

exec >"/var/log/$PROG.log" 2>&1
message "Starting server ..."

check_parameter()
{
	local v
	eval "v=\"\${$1-}\""
	[ -n "$v" ] ||
		fatal "Parameter '$1' required"
}

get_parameter()
{
	eval "printf '%s' \"\${${1}$callnum-}\""
}

resolve_target()
{
	local target="$1"
	case "${target%%/*}" in
		'')
			;;
		pipe[0-9]|pipe[0-9][0-9]|pipe[0-9][0-9][0-9])
			target="$mntdir/dst/$target"
			;;
		*)
			target="$prevdir/${target#/}"
			;;
	esac
	printf '%s' "$target"
}

run()
{
	[ -z "${DEBUG-}" ] || message "[$callnum] RUN: $*"
	"$@"
}

mkdir -p -- "$mntdir"

mountpoint -q "$mntdir" ||
	mount -t tmpfs tmpfs "$mntdir" ||:

pipenum=0
pipe="$PIPELINE"
datadir=
destdir=

while [ -n "$pipe" ]; do
	name="${pipe%%,*}"
	exe="$handlerdir/$name"

	if [ -x "$exe" ]; then
		eval "callnum=\"\${callnum_$name:-0}\""

		datadir="$mntdir/src/pipe$pipenum"
		destdir="$mntdir/dst/pipe$pipenum"

		[ "$pipenum" != 0 ] ||
			prevdir=""

		mkdir -p -- "$datadir" "$destdir"

		if ! mountpoint -q "$destdir"; then
			message "[$callnum] Handler: $exe"

			rc=0
			( . "$exe" ) || rc=$?

			if [ "$rc" != 0 ]; then
				[ "$rc" != 2 ] ||
					break
				message "[$callnum] Handler failed (rc=$rc)"
				sleep 1
				continue
			fi
		else
			message "[$callnum] Handler: $exe skipped"
		fi

		prevdir="$destdir"

		callnum=$(($callnum + 1))
		eval "callnum_$name=\"\$callnum\""
	fi

	pipe="${pipe#$name}"
	pipe="${pipe#,}"

	pipenum=$(($pipenum + 1))
done
