#!/bin/bash
#
# Converts lines from /etc/chandev.conf to hwcfg-files.
#
# This is for debugging.
# DEBUG=1

if [ -z "$DEBUG" ]; then
    HWCFG_DIR=/etc/sysconfig/hardware
    CHANDEV=/etc/chandev.conf
else
    CHANDEV=$1
    HWCFG_DIR="."
fi

if [ ! -f "$CHANDEV" ]; then
    # Nothing to be done
    exit 0
fi

# What a bastard
retval=0
saved_IFS="$IFS"
IFS=","
while read; do
    _line="$REPLY"
    set -- $REPLY
    if [ -n "$1" ]; then
	_devname=${1%%[1234567890]*}
	echo -n "Converting parameter $1: "
	shift
	case "$_devname" in
	    qeth*)
		_read_chan=$(($1))
		_write_chan=$(($2))
		_data_chan=$(($3))
		if [ "$_write_chan" -ne $(expr $_read_chan + 1) -o \
			"$_data_chan" -ne $(expr $_read_chan + 2) ]; then
		    echo "Channel IDs not consecutive, cannot convert."
		    echo "Entry was:"
		    echo "$_line"
		    retval=1
		    break;
		fi
		shift; shift; shift;
		if [ $# -gt 0 ]; then
		    if [ $1 -ne 0 ] ; then
			_memsize=$1
		    fi
		    shift;
		fi
		if [ $# -gt 0 ] ; then
		    if [ $1 -ne -1 -a $1 -ne 0 ] ; then
			_portno=$1
		    fi
		fi
		if [ "$_read_chan" -lt "$_write_chan" ]; then
		    CFG_ID="$_read_chan"
		else
		    CFG_ID="$_write_chan"
		fi
		if [ "$CFG_ID" -gt "$_data_chan" ]; then
		    CFG_ID="$_data_chan"
		fi
		_begin_id=$(printf "%04x" $CFG_ID)
		eval CFGNAME[$CFG_ID]="hwcfg-qeth-bus-ccw-0.0.$_begin_id"
		eval MODULE[$CFG_ID]="qeth_mod"
		eval STARTMODE[$CFG_ID]="auto"
		eval CCW_CHAN_NAME[$CFG_ID]="qeth"
		eval CCW_CHAN_NUM[$CFG_ID]=3
		eval CCW_CHAN_IDS[$CFG_ID]="\"0.0.$(printf "%04x" $_read_chan) 0.0.$(printf "%04x" $_write_chan) 0.0.$(printf "%04x" $_data_chan)\""
		eval SCRIPT_up[$CFG_ID]="hwup-ccw"
		eval SCRIPT_ccw[$CFG_ID]="hwup-ccw"
		eval SCRIPT_ccwgroup[$CFG_ID]="hwup-qeth"
		eval SCRIPT_down[$CFG_ID]="hwdown-ccw"
		CFG_LIST="${CFG_LIST:+$CFG_LIST }$CFG_ID"
		_entry="$_line"
		echo "ok."
		;;
	    ctc*|escon*|lcs*)
		_read_chan=$(($1))
		_write_chan=$(($2))
		if [ "$_write_chan" -ne $(expr $_read_chan + 1) ]; then
		    echo "Channel IDs not consecutive, cannot convert."
		    echo "Entry was:"
		    echo "$_line"
		    retval=1
		    break;
		fi
		shift; shift;
		if [ $# -gt 0 ]; then
		    if  [ $1 -ne 0 ]; then
			_memsize=$1
		    fi
		    shift
		fi
		if [ $# -gt 0 ]; then
		    if [ $1 -ne 0 ]; then
			_port=$1
		    fi
		    shift
		fi
		if [ $# -gt 0 ]; then
		    if [ $1 -ne 0 ]; then
			_checksum=$1
		    fi
		    shift
		fi
		if [ $# -gt 0 ] && [ $1 -ne 0 ]; then
		    _use_stats=$1
		fi
		if [ "$_read_chan" -lt "$_write_chan" ]; then
		    CFG_ID="$_read_chan"
		else
		    CFG_ID="$_write_chan"
		fi
		_begin_id=$(printf "%04x" $CFG_ID)
		eval CFGNAME[$CFG_ID]="hwcfg-$_devname-bus-ccw-0.0.$_begin_id"
		eval MODULE[$CFG_ID]="ctc"
		eval STARTMODE[$CFG_ID]="auto"
		eval CCW_CHAN_NAME[$CFG_ID]=cu3088
		eval CCW_CHAN_NUM[$CFG_ID]=2
		eval CCW_CHAN_IDS[$CFG_ID]="\"0.0.$(printf "%04x" $_read_chan) 0.0.$(printf "%04x" $_write_chan)\""
		eval CCW_CHAN_MODE[$CFG_ID]="$_port"
		eval SCRIPT_up[$CFG_ID]="hwup-ccw"
		eval SCRIPT_ccw[$CFG_ID]="hwup-ccw"
		eval SCRIPT_ccwgroup[$CFG_ID]="hwup-ctc"
		eval SCRIPT_down[$CFG_ID]="hwdown-ccw"
		CFG_LIST="${CFG_LIST:+$CFG_LIST }$CFG_ID"
		_entry="$_line"
		echo "ok."
		;;
	    add_parm*)
		_chan_type=$1
		if [ $(($_chan_type)) -ne $((0x10)) ]; then
		    echo "Unhandled device type $_chan_type in add_parms!"
		    retval=1
		    continue
		fi

		case $2 in
		    0x*)
			shift
			_begin_id=$1
			shift
			_end_id=$1
			;;
		    *)
			_begin_id=0
			_end_id=$((0xFFFF))
			;;
		esac

		while shift; do
		    case $1 in
			portname*)
			    _port=${1#portname:}
			    for _id in $CFG_LIST; do
				if [ $(($_id > $_begin_id)) ] && [ $((_id < $_end_id)) ] ; then
				    eval CCW_CHAN_MODE[$_id]="$_port"

				fi
			    done
			    echo -n "(portname: $_port) "
			    ;;
			*)
			    if [ "$1" ]; then
				echo -n "($1: ignored) "
			    fi
			    ;;
		    esac
		done
		echo "ok."
		_entry="$_entry;$_line"
		;;
	    noauto*)
		echo "ignored."
		;;
	    use_devno_names*)
		echo "ignored."
		;;
	    *)
		echo "not supported, please edit manually."
		retval=1
		;;
	esac
    fi
done < <(cat $CHANDEV | sed '/^#/d;/^ /d' | tr ";" "\n")
IFS="$saved_IFS"

for _cfg in $CFG_LIST; do
    _hwcfg_file=${HWCFG_DIR}/${CFGNAME[$_cfg]}
    cat > $_hwcfg_file <<EOF
#!/bin/sh
#
# ${CFGNAME[$_cfg]}
#
# Automatically converted from chandev entry
# $_entry
#
# Please check whether the specified adapter is 
# correctly configured
#

STARTMODE="${STARTMODE[$_cfg]}"
MODULE="${MODULE[$_cfg]}"
MODULE_OPTIONS=""
MODULE_UNLOAD="no"

# Scripts to be called for the various events.
# If called manually SCRIPTUP is selected.
EOF

    if [ $SCRIPT_up[$_cfg] ]; then
	echo "SCRIPTUP=\"${SCRIPT_up[$_cfg]}\"" >> $_hwcfg_file
    fi
    if [ $SCRIPT_ccw[$_cfg] ]; then
	echo "SCRIPTUP_ccw=\"${SCRIPT_ccw[_cfg]}\"" >> $_hwcfg_file
    fi
    if [ $SCRIPT_ccw[$_cfg] ]; then
	echo "SCRIPTUP_ccwgroup=\"${SCRIPT_ccwgroup[_cfg]}\"" >> $_hwcfg_file
    fi
    if [ ${SCRIPT_down[$_cfg]} ]; then
	echo "SCRIPTDOWN=\"${SCRIPT_down[$_cfg]}\"" >> $_hwcfg_file
    fi

    cat >> $_hwcfg_file <<EOF

# CCW_CHAN_IDS sets the channel IDs for this device
# The first ID will be used as the group ID
CCW_CHAN_IDS="${CCW_CHAN_IDS[$_cfg]}"

# CCW_CHAN_NUM set the number of channels for this device
CCW_CHAN_NUM="${CCW_CHAN_NUM[$_cfg]}"

EOF
    if [ "$_devname" = "ctc" -o "$_devname" = "escon" ]; then
	cat >> $_hwcfg_file <<EOF
# CCW_CHAN_MODE sets the protocol for CTC / ESCON
# 0 for compability mode (default)
# 1 for extended mode
# 2 for CTC-based tty
# 3 for compability mode with OS/390 and z/OS
EOF
	if [ ${CCW_CHAN_MODE[$_cfg]} ]; then
	    echo "CCW_CHAN_MODE=\"${CCW_CHAN_MODE[$_cfg]}\"" >> $_hwcfg_file
	else
	    echo "# CCW_CHAN_MODE=0" >> $_hwcfg_file
	fi
	echo >> $_hwcfg_file
    elif [ "$_devname" = "lcs" ]; then
	cat >> $_hwcfg_file <<EOF
# CCW_CHAN_MODE sets the port number for LCS
# Port number 0 is the default
EOF
	if [ ${CCW_CHAN_MODE[$_cfg]} ]; then
	    echo "CCW_CHAN_MODE=\"${CCW_CHAN_MODE[$_cfg]}\"" >> $_hwcfg_file
	else
	    echo "# CCW_CHAN_MODE=0" >> $_hwcfg_file
	fi
	echo >> $_hwcfg_file
    else
	cat >> $_hwcfg_file <<EOF
# CCW_CHAN_MODE sets the portname for OSA-Express / Hipersockets
EOF
	if [ ${CCW_CHAN_MODE[$_cfg]} ]; then
	    echo "CCW_CHAN_MODE=\"${CCW_CHAN_MODE[$_cfg]}\"" >> $_hwcfg_file
	else
	    echo "# CCW_CHAN_MODE=\"\"" >> $_hwcfg_file
	fi
	echo >> $_hwcfg_file
    fi
    echo Wrote ${CFGNAME[$_cfg]}
done

exit $retval
