#!/bin/bash

# first step:
# Read inet table and pre-paese it
sed <~/PACKAGES/xkeyboard-config-stable-noarch/BUILD/xkeyboard-config-0.9/symbols/inet >inet.tbl '
# initial comments and evdev:
1,139d
/partial alphanumeric_keys/d
/partial hidden alphanumeric_keys/d
s/XF86AudioPlay, XF86AudioPause/NEWAudioPlayPause/
s/XF86Eject, XF86Eject/XF86Eject/
s/XF86AudioStop, XF86Eject/XF86AudioStop/ # FIXME: If keyboard has no Eject, Shift+AudioStop shoud generate eject
s/XF86Reload/XF86Refresh/ # FIXME: Probably duplicate in X
s/XF86PowerOff/XF86PowerDown/ # FIXME: Probably duplicate in X
s/[[:space:]]*$//
t1
:1
s/[[:space:]]*include "inet(\(.*\))"/@INCLUDE \1/
t2
s/[[:space:]]*partial[[:space:]]*xkb_symbols[[:space:]]*"\(.*\)"[[:space:]]*{/@KEYMAP@ \1/
t2
s/[[:space:]]*xkb_symbols[[:space:]]*"\(.*\)"[[:space:]]*{/@KEYMAP@ \1/
t2
s/^[[:space:]]*key[[:space:]]*<\([^>]*\)>[[:space:]]*{[[:space:]]*\[[[:space:]]*\(.*\)[[:space:]]*\][[:space:]]*\};/KEY=\1 SYMBOL=\2/
t2
s/^};/@KEYMAPEND@/
t2
s/^[[:space:]]*$//
t2
s@[[:space:]]*//@&@
t2
s/^/PARSE ERROR: /
:2
s@//\(.*\)@# \1@
s/[[:space:]]*$//
'
rm -rf scancode_tables
mkdir -p scancode_tables

function fix_keysym {
    FIXED_KEYSYM=${1//+/__PLUS__}
    FIXED_KEYSYM=${FIXED_KEYSYM//-/__MINUS__}
    FIXED_KEYSYM=${FIXED_KEYSYM//\//__SLASH__}
}

#declare -a SCANCODES
#exec <kernel_scancodes.txt
#while read KEY SCANCODE ; do
#    SCANCODES[$KEY]=$SCANCODE
#done

echo >keycodes_inet "// $XKeyboardConfig: xkbdesc/keycodes/inet,v $

// EAK (Easy Access, Internet, Multimedia, PDA) keyboards
// Copyright (C) 2002, 2007 Stanislav Brabec <sbrabec@suse.cz>, SuSE Linux
//
// Based on LinEAK project
// LinEAK - Linux support for Easy Access and Internet Keyboards      
// Copyright (C) 2001, 2002 Mark Smulders <Mark@PIRnet.nl>
//

"


unset ${!KEYSYM_*}
exec <input_xfree86_keycodes.txt
while read KEYSYM KEYNUM ; do
    if test -n "$KEYNUM" ; then
	fix_keysym $KEYSYM
	eval KEYSYM_$FIXED_KEYSYM=$KEYNUM
    fi
done
KEYSYM_I01=$KEYSYM_XFER

exec <input_xfree86_keycodes.txt
while read KEYSYM KEYNUM ; do
    if test -n "$KEYNUM" ; then
	fix_keysym $KEYSYM
	eval KEYSYM_$FIXED_KEYSYM=$KEYNUM
    fi
done

rm -f uniq_keysyms.txt
rm -f uniq_keynames.txt
exec <input_linux_map_fixed.txt
exec >keycodes_evdev
exec 4>symbols_evdev
echo "// translation from Linux evdev keycodes to xfree86 short names.

default xkb_keycodes \"evdev\" {
    minimum = 8;
    maximum = 512;"
echo >&4 "// translation from keyboard independent keycodes from inet or evdev to key names.

default xkb_symbols \"basic\" {"
unset ${!X2LINUX_*}
while read KEYNAME KEYNUM EVDEVSYM XNAME ; do
    if test "${KEYNAME:0:1}" = \" ; then
	KEYNAME=${KEYNAME//\"}
	KEYNUM=${KEYNUM//\"}
	XNAME=${XNAME//\"}
	EVDEVSYM=${EVDEVSYM//\"}
	eval X2LINUX_KEYNAME_$XNAME\=$KEYNAME
	eval X2LINUX_KEYCODE_$XNAME\=$KEYNUM
	eval X2LINUX_EVDEVSYM_$XNAME\=\"$EVDEVSYM\"
	echo >>uniq_keysyms.txt $EVDEVSYM
	echo >>uniq_keynames.txt $XNAME
	if test "$KEYNAME" = "${KEYNAME#BTN_}" ; then
	    if test -n "$EVDEVSYM" ; then
		SPACES="    "
		SPACES=${SPACES:${#EVDEVSYM}}
		echo "    <$EVDEVSYM> $SPACES= $(( $KEYNUM + 8 ));"
		SPACES2="                     "
		SPACES2=${SPACES2:${#XNAME}}
		echo >&4 "    key <$EVDEVSYM>   $SPACES{ [ $XNAME $SPACES2] };"
	    else
		echo
	    fi
	fi
    fi
done
echo "
    // Solaris compatibility

    alias <LMTA> = <LWIN>;
    alias <RMTA> = <RWIN>;
    alias <COMP> = <MENU>;

    indicator 1 = \"Caps Lock\";
    indicator 2 = \"Num Lock\";
    indicator 3 = \"Scroll Lock\";
    alias <ALGR> = <RALT>;
};"
echo >&4 "};"

exec <inet.tbl
exec 3>>keycodes_inet
FILE=
while : ; do
    BUFFER=
    while read ; do
	if test "${REPLY:0:1}" != @ ; then
	    BUFFER="$BUFFER$REPLY
"
		echo >&3 "${REPLY/# ///}"
	else
	    break
	fi
    done
    FILE=${REPLY#@KEYMAP@ }
    if test -z "$FILE" ; then
	break
    fi
    echo >&2 $FILE
    echo >&3 "xkb_keycodes \"$FILE\" {
    include \"xfree86\""
    exec >scancode_tables/$FILE
    echo "#!/bin/sh
# setkeycodes script for $FILE
# Generated from xkeyboard-config-0.9/symbols/inet by
# map_symbols_inet_to_keycodes_inet.sh
# Author: Stanislav Brabec, SUSE Linux <sbrabec@suse.cz>
#
# Based on LinEAK project
# LinEAK - Linux support for Easy Access and Internet Keyboards      
# Copyright (C) 2001, 2002 Mark Smulders <Mark@PIRnet.nl>
#
# Verified by:
#"
    echo "$BUFFER"
    while read ; do
	if test "${REPLY:0:1}" != @ ; then
	    KEY=
	    SYMBOL=
	    eval $REPLY
	    COMMENT=${REPLY#*#}
	    if test "$COMMENT" = "$REPLY" ; then
		COMMENT=
		CCOMMENT=
		OCOMMENT=
	    else
		CCOMMENT=" #$COMMENT"
		OCOMMENT=" //$COMMENT"
	    fi
	    if test -z "$KEY" ; then
		echo "$CCOMMENT"
		echo >&3 "$OCOMMENT"
	    else
		fix_keysym $KEY
		eval KEYNUM\=\$KEYSYM_$FIXED_KEYSYM
		if test -z "$KEYNUM" ; then
		    echo "# ERROR in keymap: XNAME=$SYMBOL: Cannot assign keycodes_xfree86=$KEY to scancode!"
		    echo >&3 "// ERROR in keymap: XNAME=$SYMBOL: Cannot assign keycodes_xfree86=$KEY to scancode!"
		else
#		    SCANCODE=${SCANCODES[$KEYNUM]}
		    eval LINUX_KEYNAME\=\$X2LINUX_KEYNAME_$SYMBOL
		    eval EVDEV_KEYCODE\=\$X2LINUX_KEYCODE_$SYMBOL
		    eval EVDEV_XSYM\=\$X2LINUX_EVDEVSYM_$SYMBOL
		    eval EXT_SCANCODE=\$\(printf %02x $(( $KEYNUM & 0x7f )) \)
		    if test $KEYNUM -ge 128 ; then
			EXT_SCANCODE=e0$EXT_SCANCODE
		    fi
		    echo "# KEY_NAME=$SYMBOL LINUX_NAME=$LINUX_KEYNAME XFREE86_NAME=$KEY SCANCODE=$KEYNUM EVDEV_KEYCODE=$EVDEV_KEYCODE"
		    if test -z "$EVDEV_KEYCODE" ; then
			echo "# ERROR: Missing mapping to Linux key for $SYMBOL!"
		    else
			echo "setkeycodes $EXT_SCANCODE $EVDEV_KEYCODE$CCOMMENT"
		    fi
		fi
		if test "${#EVDEV_XSYM}" = 3 ; then
		    echo >&3 "    <$EVDEV_XSYM>  = $EVDEV_KEYCODE$OCOMMENT;"
		else
		    if test "${#EVDEV_XSYM}" = 2 ; then
			echo >&3 "    <$EVDEV_XSYM>   = $EVDEV_KEYCODE$OCOMMENT;"
		    else
			echo >&3 "    <$EVDEV_XSYM> = $EVDEV_KEYCODE$OCOMMENT;"
		    fi
		fi
	    fi
	else
	    if test "${REPLY%% *}" = @INCLUDE ; then
		echo "source ${REPLY#* }"
		echo >&3 "    include \"inet(${REPLY#* })\""
	    else
		echo >&3 "};"
		break
	    fi
	fi
    done
    if test "$REPLY" != "@KEYMAPEND@" ; then
	echo "ERROR: $REPLY"
    fi
done

echo >&2 "
Possible duplicates:"
sort uniq_keynames.txt | uniq -d >&2
sort uniq_keysyms.txt | uniq -d >&2

echo >&2 "
Undefined X keys:"
grep -h ERROR scancode_tables/* | sed -n 's/!//;s/# ERROR: Missing mapping to Linux key for //p' | sort -u | tee missing_linux.txt >&2
