hal: Branch 'master'

Richard Hughes hughsient at kemper.freedesktop.org
Tue Jun 5 09:03:43 PDT 2007


 configure.in                        |   16 
 doc/spec/hal-spec-properties.xml    |   39 +
 fdi/policy/10osvendor/10-keymap.fdi |    9 
 fdi/policy/10osvendor/Makefile.am   |    4 
 tools/.gitignore                    |    3 
 tools/Makefile.am                   |   33 +
 tools/hal-setup-keymap-hash-name.h  |  991 ++++++++++++++++++++++++++++++++++++
 tools/hal-setup-keymap.c            |  154 +++++
 8 files changed, 1249 insertions(+)

New commits:
diff-tree 8670a01517bb33d046cfb6416de13c411e6a3f6c (from 21edb06bbf0e24a1c1c9948c2a8e73b58ebbb516)
Author: Richard Hughes <richard at hughsie.com>
Date:   Tue Jun 5 17:04:11 2007 +0100

    add keymap capabilities into hal
    
    Add keymapping infrastructure into hal so we can remap scancode->keycodes
    at boot time, fixing many multimedia keyboards. Thanks to everybody who
    helped review this.

diff --git a/configure.in b/configure.in
index b2adc77..cd8c80c 100644
--- a/configure.in
+++ b/configure.in
@@ -470,6 +470,21 @@ if test "x$enable_console_kit" != "xno";
    msg_conkit=yes
 fi
 
+AC_ARG_WITH([keymaps], AS_HELP_STRING([--with-keymaps], [Re-map multimedia keys (auto)]))
+BUILD_KEYMAPS=no
+if test "x$with_keymaps" = "xyes" ; then
+   BUILD_KEYMAPS=yes
+elif test "x$with_keymaps" = "x" ; then
+  case "${HALD_BACKEND}" in
+    linux)
+      BUILD_KEYMAPS=yes
+      ;;
+    *)
+      ;;
+  esac
+fi
+AM_CONDITIONAL(BUILD_KEYMAPS, [test x$BUILD_KEYMAPS = xyes])
+
 # check for PolicyKit
 AM_CONDITIONAL(HAVE_POLKIT, [false])
 AC_ARG_ENABLE([policy-kit],
@@ -989,6 +1004,7 @@ echo "
         Macbook Pro utils:           ${BUILD_MACBOOKPRO} (Linux only, x86 only, requires libpci)
         OMAP utils:                  ${BUILD_OMAP} (Linux only, arm only)
         CPU frequency scaling:       ${BUILD_CPUFREQ} (Linux only)
+        Re-map multimedia keys:      ${BUILD_KEYMAPS} (Linux only)
         Forward IBM ACPI events:     ${BUILD_ACPI_IBM} (Linux only)
         Forward Toshiba ACPI events: ${BUILD_ACPI_TOSHIBA} (Linux only)
 	USB wireless mouse power:    ${BUILD_USBCSR} (Linux only, requires libusb)
diff --git a/doc/spec/hal-spec-properties.xml b/doc/spec/hal-spec-properties.xml
index 8c40ecb..65d4bde 100644
--- a/doc/spec/hal-spec-properties.xml
+++ b/doc/spec/hal-spec-properties.xml
@@ -4599,6 +4599,45 @@ org.freedesktop.Hal.Device.Volume.method
         properties.
       </para>
     </sect2>
+    <sect2 id="device-properties-input-keymap">
+      <title>
+        input.keymap namespace
+      </title>
+      <para>
+        Device objects with the capability <literal>input.keymap</literal>
+        provide facilities to remap keyboard buttons.
+      </para>
+      <informaltable>
+        <tgroup cols="2">
+          <thead>
+            <row>
+              <entry>Key (type)</entry>
+              <entry>Values</entry>
+              <entry>Mandatory</entry>
+              <entry>Description</entry>
+            </row>
+          </thead>
+          <tbody>
+            <row>
+              <entry>
+                <literal>input.keymap.data</literal> (strlist)
+              </entry>
+              <entry>e.g. "e017:brightnessup"</entry>
+              <entry>No</entry>
+              <entry>
+                The scancode is represented in hex and the keycode name as
+                as string. The keycode name is not case sensitive.
+                On Linux, the keycode name should be the same constant as
+                present in /usr/include/linux/input.h with the 'KEY_'
+                prefix removed, e.g. 'KEY_SLEEP' -> 'sleep'.
+                You can append as many <literal>input.keymap.data</literal>
+                values as there are keys to remap.
+              </entry>
+            </row>
+          </tbody>
+        </tgroup>
+      </informaltable>
+    </sect2>
     <sect2 id="device-properties-pcmcia_socket">
       <title>
         pcmcia_socket namespace
diff --git a/fdi/policy/10osvendor/10-keymap.fdi b/fdi/policy/10osvendor/10-keymap.fdi
new file mode 100644
index 0000000..9b92b1b
--- /dev/null
+++ b/fdi/policy/10osvendor/10-keymap.fdi
@@ -0,0 +1,9 @@
+<?xml version="1.0" encoding="ISO-8859-1"?> <!-- -*- SGML -*- -->
+<deviceinfo version="0.2">
+  <device>
+    <match key="info.capabilities" contains="input.keymap">
+      <append key="info.callouts.add" type="strlist">hal-setup-keymap</append>
+    </match>
+  </device>
+</deviceinfo>
+
diff --git a/fdi/policy/10osvendor/Makefile.am b/fdi/policy/10osvendor/Makefile.am
index eda99fd..f3c7676 100644
--- a/fdi/policy/10osvendor/Makefile.am
+++ b/fdi/policy/10osvendor/Makefile.am
@@ -9,6 +9,10 @@ dist_fdi_DATA = 			\
 	15-storage-luks.fdi		\
 	20-storage-methods.fdi
 
+if BUILD_KEYMAPS
+dist_fdi_DATA += 10-keymap.fdi
+endif
+
 if BUILD_MACBOOKPRO
 dist_fdi_DATA += 10-macbookpro-utils.fdi
 endif
diff --git a/tools/.gitignore b/tools/.gitignore
index ca09228..dfd1e34 100644
--- a/tools/.gitignore
+++ b/tools/.gitignore
@@ -16,6 +16,9 @@ hal-is-caller-locked-out
 hal-lock
 hal-luks-remove
 hal-luks-setup
+hal-setup-keymap
+hal-setup-keymap-hash-name.gperf
+hal-setup-keymap-keys.txt
 hal-system-power-pmu
 hal-system-sonypic
 hal-policy-is-privileged
diff --git a/tools/Makefile.am b/tools/Makefile.am
index 0744f9c..6897eb6 100644
--- a/tools/Makefile.am
+++ b/tools/Makefile.am
@@ -33,10 +33,17 @@ bin_PROGRAMS =                    \
 	hal-lock		  \
 	hal-disable-polling
 
+BUILT_SOURCES = 
+DISTCLEANFILES = 
+
 if HAVE_POLKIT
 bin_PROGRAMS += hal-is-caller-privileged
 endif
 
+if BUILD_KEYMAPS
+bin_PROGRAMS += hal-setup-keymap
+endif
+
 lshal_SOURCES = lshal.c
 lshal_LDADD = @GLIB_LIBS@ $(top_builddir)/libhal/libhal.la
 
@@ -69,6 +76,22 @@ hal_is_caller_privileged_SOURCES = hal-i
 hal_is_caller_privileged_LDADD = @GLIB_LIBS@ @DBUS_LIBS@ $(top_builddir)/libhal/libhal.la
 endif
 
+if BUILD_KEYMAPS
+
+hal-setup-keymap-keys.txt: /usr/include/linux/input.h
+	awk '/^#define.*KEY_/ { if ($$2 != "KEY_MAX") { print substr($$2, 5) } }' < $< > $@
+
+hal-setup-keymap-hash-name.gperf: hal-setup-keymap-keys.txt
+	awk 'BEGIN{ print "struct key { const char* name; unsigned short id; };"; print "%null-strings"; print "%%";} { print $$1 ", KEY_" $$1 }' < $< > $@
+
+hal-setup-keymap-hash-name.h: hal-setup-keymap-hash-name.gperf
+	gperf -t --ignore-case -N lookup_key -H hash_input_names -p -C < $< > $@
+
+hal_setup_keymap_SOURCES = hal-setup-keymap.c hal-setup-keymap-hash-name.h
+hal_setup_keymap_LDADD = $(top_builddir)/libhal/libhal.la
+
+endif
+
 libexec_PROGRAMS =                          \
 	hal-storage-mount	            \
 	hal-storage-unmount 	            \
@@ -154,6 +177,16 @@ umount_hal_SOURCES = umount-hal.c
 umount_hal_LDADD = @DBUS_LIBS@ $(top_builddir)/libhal/libhal.la $(top_builddir)/libhal-storage/libhal-storage.la
 endif
 
+DISTCLEANFILES += 				\
+	hal-setup-keymap-hash-name.h		\
+	hal-setup-keymap-hash-name.gperf	\
+	hal-setup-keymap-keys.txt
+
+BUILT_SOURCES += 				\
+	hal-setup-keymap-hash-name.h		\
+	hal-setup-keymap-hash-name.gperf	\
+	hal-setup-keymap-keys.txt
+
 check:
 	for f in $(script_SCRIPTS); do \
             echo -n "Validate bash syntax in $$f : "; \
diff --git a/tools/hal-setup-keymap-hash-name.h b/tools/hal-setup-keymap-hash-name.h
new file mode 100644
index 0000000..6057183
--- /dev/null
+++ b/tools/hal-setup-keymap-hash-name.h
@@ -0,0 +1,991 @@
+/* C code produced by gperf version 3.0.2 */
+/* Command-line: gperf -t --ignore-case -N lookup_key -H hash_input_names -p -C  */
+/* Computed positions: -k'1-3,5,$' */
+
+#if !((' ' == 32) && ('!' == 33) && ('"' == 34) && ('#' == 35) \
+      && ('%' == 37) && ('&' == 38) && ('\'' == 39) && ('(' == 40) \
+      && (')' == 41) && ('*' == 42) && ('+' == 43) && (',' == 44) \
+      && ('-' == 45) && ('.' == 46) && ('/' == 47) && ('0' == 48) \
+      && ('1' == 49) && ('2' == 50) && ('3' == 51) && ('4' == 52) \
+      && ('5' == 53) && ('6' == 54) && ('7' == 55) && ('8' == 56) \
+      && ('9' == 57) && (':' == 58) && (';' == 59) && ('<' == 60) \
+      && ('=' == 61) && ('>' == 62) && ('?' == 63) && ('A' == 65) \
+      && ('B' == 66) && ('C' == 67) && ('D' == 68) && ('E' == 69) \
+      && ('F' == 70) && ('G' == 71) && ('H' == 72) && ('I' == 73) \
+      && ('J' == 74) && ('K' == 75) && ('L' == 76) && ('M' == 77) \
+      && ('N' == 78) && ('O' == 79) && ('P' == 80) && ('Q' == 81) \
+      && ('R' == 82) && ('S' == 83) && ('T' == 84) && ('U' == 85) \
+      && ('V' == 86) && ('W' == 87) && ('X' == 88) && ('Y' == 89) \
+      && ('Z' == 90) && ('[' == 91) && ('\\' == 92) && (']' == 93) \
+      && ('^' == 94) && ('_' == 95) && ('a' == 97) && ('b' == 98) \
+      && ('c' == 99) && ('d' == 100) && ('e' == 101) && ('f' == 102) \
+      && ('g' == 103) && ('h' == 104) && ('i' == 105) && ('j' == 106) \
+      && ('k' == 107) && ('l' == 108) && ('m' == 109) && ('n' == 110) \
+      && ('o' == 111) && ('p' == 112) && ('q' == 113) && ('r' == 114) \
+      && ('s' == 115) && ('t' == 116) && ('u' == 117) && ('v' == 118) \
+      && ('w' == 119) && ('x' == 120) && ('y' == 121) && ('z' == 122) \
+      && ('{' == 123) && ('|' == 124) && ('}' == 125) && ('~' == 126))
+/* The character set is not based on ISO-646.  */
+error "gperf generated tables don't work with this execution character set. Please report a bug to <bug-gnu-gperf at gnu.org>."
+#endif
+
+struct key { const char* name; unsigned short id; };
+
+#define TOTAL_KEYWORDS 346
+#define MIN_WORD_LENGTH 1
+#define MAX_WORD_LENGTH 16
+#define MIN_HASH_VALUE 1
+#define MAX_HASH_VALUE 1796
+/* maximum key range = 1796, duplicates = 0 */
+
+#ifndef GPERF_DOWNCASE
+#define GPERF_DOWNCASE 1
+static unsigned char gperf_downcase[256] =
+  {
+      0,   1,   2,   3,   4,   5,   6,   7,   8,   9,  10,  11,  12,  13,  14,
+     15,  16,  17,  18,  19,  20,  21,  22,  23,  24,  25,  26,  27,  28,  29,
+     30,  31,  32,  33,  34,  35,  36,  37,  38,  39,  40,  41,  42,  43,  44,
+     45,  46,  47,  48,  49,  50,  51,  52,  53,  54,  55,  56,  57,  58,  59,
+     60,  61,  62,  63,  64,  97,  98,  99, 100, 101, 102, 103, 104, 105, 106,
+    107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121,
+    122,  91,  92,  93,  94,  95,  96,  97,  98,  99, 100, 101, 102, 103, 104,
+    105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119,
+    120, 121, 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134,
+    135, 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149,
+    150, 151, 152, 153, 154, 155, 156, 157, 158, 159, 160, 161, 162, 163, 164,
+    165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175, 176, 177, 178, 179,
+    180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191, 192, 193, 194,
+    195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, 206, 207, 208, 209,
+    210, 211, 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, 223, 224,
+    225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239,
+    240, 241, 242, 243, 244, 245, 246, 247, 248, 249, 250, 251, 252, 253, 254,
+    255
+  };
+#endif
+
+#ifndef GPERF_CASE_STRCMP
+#define GPERF_CASE_STRCMP 1
+static int
+gperf_case_strcmp (s1, s2)
+     register const char *s1;
+     register const char *s2;
+{
+  for (;;)
+    {
+      unsigned char c1 = gperf_downcase[(unsigned char)*s1++];
+      unsigned char c2 = gperf_downcase[(unsigned char)*s2++];
+      if (c1 != 0 && c1 == c2)
+        continue;
+      return (int)c1 - (int)c2;
+    }
+}
+#endif
+
+#ifdef __GNUC__
+__inline
+#else
+#ifdef __cplusplus
+inline
+#endif
+#endif
+static unsigned int
+hash_input_names (str, len)
+     register const char *str;
+     register unsigned int len;
+{
+  static const unsigned short asso_values[] =
+    {
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,   85,  260,
+        60,  305,  130,  250,  125,  180,  360,   25,   25, 1797,
+      1797, 1797, 1797, 1797, 1797,   35,  210,   75,   15,   10,
+       235,  265,  145,  300,  295,  310,  135,   30,   95,    5,
+        50,  200,    0,   20,   40,   80,  405,  455,  428,  320,
+       190, 1797, 1797, 1797, 1797, 1797,   25,   35,  210,   75,
+        15,   10,  235,  265,  145,  300,  295,  310,  135,   30,
+        95,    5,   50,  200,    0,   20,   40,   80,  405,  455,
+       428,  320,  190, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797, 1797,
+      1797, 1797, 1797, 1797, 1797, 1797, 1797
+    };
+  register int hval = len;
+
+  switch (hval)
+    {
+      default:
+        hval += asso_values[(unsigned char)str[4]];
+      /*FALLTHROUGH*/
+      case 4:
+      case 3:
+        hval += asso_values[(unsigned char)str[2]+1];
+      /*FALLTHROUGH*/
+      case 2:
+        hval += asso_values[(unsigned char)str[1]];
+      /*FALLTHROUGH*/
+      case 1:
+        hval += asso_values[(unsigned char)str[0]];
+        break;
+    }
+  return hval + asso_values[(unsigned char)str[len - 1]];
+}
+
+#ifdef __GNUC__
+__inline
+#endif
+const struct key *
+lookup_key (str, len)
+     register const char *str;
+     register unsigned int len;
+{
+  static const struct key wordlist[] =
+    {
+      {(char*)0},
+      {"R", KEY_R},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"O", KEY_O},
+      {"RO", KEY_RO},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"E", KEY_E},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"REDO", KEY_REDO},
+      {(char*)0},
+      {"D", KEY_D},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"RED", KEY_RED},
+      {(char*)0}, {(char*)0},
+      {"S", KEY_S},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"RECORD", KEY_RECORD},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"9", KEY_9},
+      {(char*)0}, {(char*)0},
+      {"SEND", KEY_SEND},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"MODE", KEY_MODE},
+      {"RADIO", KEY_RADIO},
+      {"M", KEY_M},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"A", KEY_A},
+      {(char*)0},
+      {"RESERVED", KEY_RESERVED},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"T", KEY_T},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"DEL_EOS", KEY_DEL_EOS},
+      {(char*)0},
+      {"DOCUMENTS", KEY_DOCUMENTS},
+      {"MACRO", KEY_MACRO},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"MESSENGER", KEY_MESSENGER},
+      {(char*)0},
+      {"P", KEY_P},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"MSDOS", KEY_MSDOS},
+      {(char*)0},
+      {"CD", KEY_CD},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"DELETE", KEY_DELETE},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"DELETEFILE", KEY_DELETEFILE},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"2", KEY_2},
+      {(char*)0},
+      {"ESC", KEY_ESC},
+      {(char*)0},
+      {"MEDIA", KEY_MEDIA},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"MENU", KEY_MENU},
+      {"TUNER", KEY_TUNER},
+      {(char*)0},
+      {"RESTART", KEY_RESTART},
+      {"END", KEY_END},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"PROGRAM", KEY_PROGRAM},
+      {(char*)0}, {(char*)0},
+      {"AUDIO", KEY_AUDIO},
+      {(char*)0},
+      {"CONNECT", KEY_CONNECT},
+      {"DOT", KEY_DOT},
+      {"MEMO", KEY_MEMO},
+      {"PROPS", KEY_PROPS},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"PASTE", KEY_PASTE},
+      {"C", KEY_C},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"U", KEY_U},
+      {(char*)0}, {(char*)0},
+      {"STOP", KEY_STOP},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"0", KEY_0},
+      {"SUSPEND", KEY_SUSPEND},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"SPREADSHEET", KEY_SPREADSHEET},
+      {(char*)0},
+      {"SAT", KEY_SAT},
+      {(char*)0}, {(char*)0},
+      {"SELECT", KEY_SELECT},
+      {"UP", KEY_UP},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"ENTER", KEY_ENTER},
+      {"N", KEY_N},
+      {(char*)0}, {(char*)0},
+      {"UNDO", KEY_UNDO},
+      {"APOSTROPHE", KEY_APOSTROPHE},
+      {(char*)0},
+      {"COMPOSE", KEY_COMPOSE},
+      {(char*)0},
+      {"SAT2", KEY_SAT2},
+      {(char*)0}, {(char*)0},
+      {"PC", KEY_PC},
+      {(char*)0},
+      {"MUTE", KEY_MUTE},
+      {"SPORT", KEY_SPORT},
+      {"STOPCD", KEY_STOPCD},
+      {"DEL_EOL", KEY_DEL_EOL},
+      {"DEL_LINE", KEY_DEL_LINE},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"SETUP", KEY_SETUP},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"CALC", KEY_CALC},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"PROG2", KEY_PROG2},
+      {"SCREEN", KEY_SCREEN},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"HELP", KEY_HELP},
+      {(char*)0},
+      {"OPTION", KEY_OPTION},
+      {(char*)0},
+      {"CALENDAR", KEY_CALENDAR},
+      {(char*)0}, {(char*)0},
+      {"CAMERA", KEY_CAMERA},
+      {"HP", KEY_HP},
+      {(char*)0}, {(char*)0},
+      {"COMMA", KEY_COMMA},
+      {"6", KEY_6},
+      {(char*)0}, {(char*)0},
+      {"LAST", KEY_LAST},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"HOME", KEY_HOME},
+      {"HANJA", KEY_HANJA},
+      {"4", KEY_4},
+      {(char*)0},
+      {"COMPUTER", KEY_COMPUTER},
+      {(char*)0}, {(char*)0},
+      {"CANCEL", KEY_CANCEL},
+      {(char*)0},
+      {"ALTERASE", KEY_ALTERASE},
+      {"SHOP", KEY_SHOP},
+      {"PHONE", KEY_PHONE},
+      {"L", KEY_L},
+      {(char*)0},
+      {"LANGUAGE", KEY_LANGUAGE},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"CUT", KEY_CUT},
+      {"ZOOM", KEY_ZOOM},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"CLOSE", KEY_CLOSE},
+      {(char*)0},
+      {"F9", KEY_F9},
+      {"SENDFILE", KEY_SENDFILE},
+      {"TAPE", KEY_TAPE},
+      {(char*)0},
+      {"H", KEY_H},
+      {"CLOSECD", KEY_CLOSECD},
+      {(char*)0},
+      {"ZOOMRESET", KEY_ZOOMRESET},
+      {(char*)0},
+      {"HENKAN", KEY_HENKAN},
+      {"ZOOMOUT", KEY_ZOOMOUT},
+      {(char*)0},
+      {"BACKSPACE", KEY_BACKSPACE},
+      {"ANGLE", KEY_ANGLE},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"SEMICOLON", KEY_SEMICOLON},
+      {"SPACE", KEY_SPACE},
+      {(char*)0}, {(char*)0},
+      {"SCROLLUP", KEY_SCROLLUP},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"HOMEPAGE", KEY_HOMEPAGE},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"FORWARD", KEY_FORWARD},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"BRL_DOT2", KEY_BRL_DOT2},
+      {"BOOKMARKS", KEY_BOOKMARKS},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"EDITOR", KEY_EDITOR},
+      {(char*)0}, {(char*)0},
+      {"ZENKAKUHANKAKU", KEY_ZENKAKUHANKAKU},
+      {(char*)0}, {(char*)0},
+      {"HANGEUL", KEY_HANGEUL},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"PAGEDOWN", KEY_PAGEDOWN},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"SCROLLDOWN", KEY_SCROLLDOWN},
+      {(char*)0},
+      {"F2", KEY_F2},
+      {"DATABASE", KEY_DATABASE},
+      {"GOTO", KEY_GOTO},
+      {(char*)0},
+      {"7", KEY_7},
+      {(char*)0},
+      {"TAB", KEY_TAB},
+      {"EDIT", KEY_EDIT},
+      {"PROG4", KEY_PROG4},
+      {"PAGEUP", KEY_PAGEUP},
+      {"ARCHIVE", KEY_ARCHIVE},
+      {(char*)0},
+      {"FN_E", KEY_FN_E},
+      {"FRONT", KEY_FRONT},
+      {"COFFEE", KEY_COFFEE},
+      {(char*)0}, {(char*)0},
+      {"FN_D", KEY_FN_D},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"ISO", KEY_ISO},
+      {"FN_S", KEY_FN_S},
+      {"MINUS", KEY_MINUS},
+      {"Z", KEY_Z},
+      {(char*)0}, {(char*)0},
+      {"TEEN", KEY_TEEN},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"BRL_DOT6", KEY_BRL_DOT6},
+      {"OPEN", KEY_OPEN},
+      {(char*)0},
+      {"ADDRESSBOOK", KEY_ADDRESSBOOK},
+      {(char*)0},
+      {"BRL_DOT4", KEY_BRL_DOT4},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"Q", KEY_Q},
+      {"PRESENTATION", KEY_PRESENTATION},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"HANGUEL", KEY_HANGUEL},
+      {(char*)0}, {(char*)0},
+      {"FN_F9", KEY_FN_F9},
+      {"PLAYER", KEY_PLAYER},
+      {(char*)0},
+      {"KP9", KEY_KP9},
+      {"TEXT", KEY_TEXT},
+      {(char*)0}, {(char*)0},
+      {"UNKNOWN", KEY_UNKNOWN},
+      {(char*)0},
+      {"FN_2", KEY_FN_2},
+      {(char*)0},
+      {"B", KEY_B},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"FN", KEY_FN},
+      {"MHP", KEY_MHP},
+      {(char*)0},
+      {"PRINT", KEY_PRINT},
+      {"VENDOR", KEY_VENDOR},
+      {(char*)0},
+      {"YEN", KEY_YEN},
+      {"BACKSLASH", KEY_BACKSLASH},
+      {(char*)0}, {(char*)0},
+      {"REFRESH", KEY_REFRESH},
+      {(char*)0}, {(char*)0},
+      {"GAMES", KEY_GAMES},
+      {"FORWARDMAIL", KEY_FORWARDMAIL},
+      {(char*)0},
+      {"BRL_DOT7", KEY_BRL_DOT7},
+      {(char*)0},
+      {"TITLE", KEY_TITLE},
+      {(char*)0},
+      {"KPCOMMA", KEY_KPCOMMA},
+      {"DVD", KEY_DVD},
+      {"TIME", KEY_TIME},
+      {"CLEAR", KEY_CLEAR},
+      {(char*)0},
+      {"CYCLEWINDOWS", KEY_CYCLEWINDOWS},
+      {(char*)0},
+      {"LEFT", KEY_LEFT},
+      {"KPDOT", KEY_KPDOT},
+      {"FN_ESC", KEY_FN_ESC},
+      {"AB", KEY_AB},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"PLAYPAUSE", KEY_PLAYPAUSE},
+      {"SOUND", KEY_SOUND},
+      {"SEARCH", KEY_SEARCH},
+      {(char*)0}, {(char*)0},
+      {"NEXT", KEY_NEXT},
+      {(char*)0},
+      {"F", KEY_F},
+      {(char*)0},
+      {"EPG", KEY_EPG},
+      {"CHAT", KEY_CHAT},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"PVR", KEY_PVR},
+      {"LEFTSHIFT", KEY_LEFTSHIFT},
+      {"FN_F2", KEY_FN_F2},
+      {"INSERT", KEY_INSERT},
+      {(char*)0},
+      {"LEFTMETA", KEY_LEFTMETA},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"F6", KEY_F6},
+      {"POWER", KEY_POWER},
+      {(char*)0}, {(char*)0},
+      {"PLAYCD", KEY_PLAYCD},
+      {"LEFTALT", KEY_LEFTALT},
+      {"SUBTITLE", KEY_SUBTITLE},
+      {(char*)0},
+      {"SLEEP", KEY_SLEEP},
+      {(char*)0},
+      {"F4", KEY_F4},
+      {(char*)0},
+      {"MAIL", KEY_MAIL},
+      {"GRAVE", KEY_GRAVE},
+      {"5", KEY_5},
+      {(char*)0},
+      {"VCR", KEY_VCR},
+      {"MOVE", KEY_MOVE},
+      {"RIGHTBRACE", KEY_RIGHTBRACE},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"BRL_DOT5", KEY_BRL_DOT5},
+      {"DIRECTION", KEY_DIRECTION},
+      {"PAUSE", KEY_PAUSE},
+      {(char*)0}, {(char*)0},
+      {"MP3", KEY_MP3},
+      {"LIST", KEY_LIST},
+      {(char*)0},
+      {"1", KEY_1},
+      {"PAUSECD", KEY_PAUSECD},
+      {"BRL_DOT1", KEY_BRL_DOT1},
+      {"SAVE", KEY_SAVE},
+      {"EMAIL", KEY_EMAIL},
+      {"DIGITS", KEY_DIGITS},
+      {(char*)0},
+      {"VOLUMEUP", KEY_VOLUMEUP},
+      {"RIGHTMETA", KEY_RIGHTMETA},
+      {"RIGHT", KEY_RIGHT},
+      {"G", KEY_G},
+      {(char*)0},
+      {"RIGHTALT", KEY_RIGHTALT},
+      {(char*)0},
+      {"RIGHTSHIFT", KEY_RIGHTSHIFT},
+      {(char*)0}, {(char*)0},
+      {"KEYBOARD", KEY_KEYBOARD},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"WORDPROCESSOR", KEY_WORDPROCESSOR},
+      {"BASSBOOST", KEY_BASSBOOST},
+      {(char*)0}, {(char*)0},
+      {"DOWN", KEY_DOWN},
+      {"F19", KEY_F19},
+      {"POWER2", KEY_POWER2},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"REWIND", KEY_REWIND},
+      {(char*)0}, {(char*)0},
+      {"NEWS", KEY_NEWS},
+      {(char*)0},
+      {"FIND", KEY_FIND},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"VCR2", KEY_VCR2},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"BRL_DOT3", KEY_BRL_DOT3},
+      {"FN_B", KEY_FN_B},
+      {"SCROLLLOCK", KEY_SCROLLLOCK},
+      {"FASTFORWARD", KEY_FASTFORWARD},
+      {(char*)0}, {(char*)0},
+      {"BACK", KEY_BACK},
+      {"VOLUMEDOWN", KEY_VOLUMEDOWN},
+      {(char*)0},
+      {"KPMINUS", KEY_KPMINUS},
+      {(char*)0},
+      {"FILE", KEY_FILE},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"CHANNELUP", KEY_CHANNELUP},
+      {(char*)0}, {(char*)0},
+      {"KPSLASH", KEY_KPSLASH},
+      {"INS_LINE", KEY_INS_LINE},
+      {(char*)0}, {(char*)0},
+      {"J", KEY_J},
+      {"NUMLOCK", KEY_NUMLOCK},
+      {(char*)0},
+      {"FN_F", KEY_FN_F},
+      {(char*)0}, {(char*)0},
+      {"F7", KEY_F7},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"I", KEY_I},
+      {"EJECTCD", KEY_EJECTCD},
+      {(char*)0},
+      {"COPY", KEY_COPY},
+      {(char*)0}, {(char*)0},
+      {"EJECTCLOSECD", KEY_EJECTCLOSECD},
+      {"MUHENKAN", KEY_MUHENKAN},
+      {(char*)0},
+      {"FN_F6", KEY_FN_F6},
+      {"3", KEY_3},
+      {(char*)0},
+      {"PREVIOUS", KEY_PREVIOUS},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"F21", KEY_F21},
+      {"FN_1", KEY_FN_1},
+      {"FN_F4", KEY_FN_F4},
+      {"K", KEY_K},
+      {(char*)0},
+      {"BRL_DOT8", KEY_BRL_DOT8},
+      {(char*)0},
+      {"PROG1", KEY_PROG1},
+      {(char*)0},
+      {"OK", KEY_OK},
+      {"LEFTCTRL", KEY_LEFTCTRL},
+      {"RIGHTCTRL", KEY_RIGHTCTRL},
+      {(char*)0},
+      {"CHANNELDOWN", KEY_CHANNELDOWN},
+      {(char*)0}, {(char*)0},
+      {"GRAPHICSEDITOR", KEY_GRAPHICSEDITOR},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"LEFTBRACE", KEY_LEFTBRACE},
+      {"FIRST", KEY_FIRST},
+      {"Y", KEY_Y},
+      {"KPENTER", KEY_KPENTER},
+      {"F20", KEY_F20},
+      {(char*)0}, {(char*)0},
+      {"ZOOMIN", KEY_ZOOMIN},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"FINANCE", KEY_FINANCE},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"CONFIG", KEY_CONFIG},
+      {(char*)0},
+      {"QUESTION", KEY_QUESTION},
+      {(char*)0},
+      {"SLASH", KEY_SLASH},
+      {(char*)0},
+      {"BATTERY", KEY_BATTERY},
+      {"F22", KEY_F22},
+      {"SLOW", KEY_SLOW},
+      {(char*)0},
+      {"KPPLUS", KEY_KPPLUS},
+      {"CHANNEL", KEY_CHANNEL},
+      {"KP6", KEY_KP6},
+      {"INFO", KEY_INFO},
+      {(char*)0},
+      {"KPPLUSMINUS", KEY_KPPLUSMINUS},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"F24", KEY_F24},
+      {(char*)0}, {(char*)0},
+      {"FN_F12", KEY_FN_F12},
+      {(char*)0},
+      {"KP1", KEY_KP1},
+      {(char*)0},
+      {"102ND", KEY_102ND},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"KBDILLUMTOGGLE", KEY_KBDILLUMTOGGLE},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"GREEN", KEY_GREEN},
+      {(char*)0}, {(char*)0},
+      {"LINEFEED", KEY_LINEFEED},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"AGAIN", KEY_AGAIN},
+      {"FN_F10", KEY_FN_F10},
+      {(char*)0},
+      {"KP0", KEY_KP0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"BRIGHTNESSUP", KEY_BRIGHTNESSUP},
+      {(char*)0}, {(char*)0},
+      {"PROG3", KEY_PROG3},
+      {(char*)0}, {(char*)0},
+      {"NEXTSONG", KEY_NEXTSONG},
+      {"PLAY", KEY_PLAY},
+      {"FN_F7", KEY_FN_F7},
+      {"8", KEY_8},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"KBDILLUMUP", KEY_KBDILLUMUP},
+      {(char*)0}, {(char*)0},
+      {"KP2", KEY_KP2},
+      {(char*)0},
+      {"VIDEO", KEY_VIDEO},
+      {"KPLEFTPAREN", KEY_KPLEFTPAREN},
+      {(char*)0},
+      {"F23", KEY_F23},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"F5", KEY_F5},
+      {"KP5", KEY_KP5},
+      {"DIRECTORY", KEY_DIRECTORY},
+      {"VIDEOPHONE", KEY_VIDEOPHONE},
+      {(char*)0}, {(char*)0},
+      {"KP4", KEY_KP4},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"KP8", KEY_KP8},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"KPRIGHTPAREN", KEY_KPRIGHTPAREN},
+      {(char*)0},
+      {"FAVORITES", KEY_FAVORITES},
+      {(char*)0}, {(char*)0},
+      {"F1", KEY_F1},
+      {(char*)0},
+      {"BRIGHTNESSDOWN", KEY_BRIGHTNESSDOWN},
+      {(char*)0},
+      {"WAKEUP", KEY_WAKEUP},
+      {(char*)0},
+      {"CAPSLOCK", KEY_CAPSLOCK},
+      {"BLUE", KEY_BLUE},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"KBDILLUMDOWN", KEY_KBDILLUMDOWN},
+      {"HIRAGANA", KEY_HIRAGANA},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"EXIT", KEY_EXIT},
+      {"KATAKANA", KEY_KATAKANA},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"SYSRQ", KEY_SYSRQ},
+      {"KATAKANAHIRAGANA", KEY_KATAKANAHIRAGANA},
+      {(char*)0}, {(char*)0},
+      {"KPJPCOMMA", KEY_KPJPCOMMA},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"KP3", KEY_KP3},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"F16", KEY_F16},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"V", KEY_V},
+      {(char*)0},
+      {"TV2", KEY_TV2},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"KPEQUAL", KEY_KPEQUAL},
+      {"F11", KEY_F11},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"SHUFFLE", KEY_SHUFFLE},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"YELLOW", KEY_YELLOW},
+      {(char*)0}, {(char*)0},
+      {"TWEN", KEY_TWEN},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"F10", KEY_F10},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"F3", KEY_F3},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"TV", KEY_TV},
+      {(char*)0}, {(char*)0},
+      {"REPLY", KEY_REPLY},
+      {(char*)0},
+      {"X", KEY_X},
+      {(char*)0},
+      {"VOICEMAIL", KEY_VOICEMAIL},
+      {"FN_F5", KEY_FN_F5},
+      {(char*)0},
+      {"PREVIOUSSONG", KEY_PREVIOUSSONG},
+      {"F12", KEY_F12},
+      {(char*)0}, {(char*)0},
+      {"AUX", KEY_AUX},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"SWITCHVIDEOMODE", KEY_SWITCHVIDEOMODE},
+      {(char*)0}, {(char*)0},
+      {"F15", KEY_F15},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"F14", KEY_F14},
+      {(char*)0},
+      {"FN_F1", KEY_FN_F1},
+      {"FN_F11", KEY_FN_F11},
+      {(char*)0},
+      {"F18", KEY_F18},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"EQUAL", KEY_EQUAL},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"WLAN", KEY_WLAN},
+      {(char*)0}, {(char*)0},
+      {"XFER", KEY_XFER},
+      {"KP7", KEY_KP7},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"W", KEY_W},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"MIN_INTERESTING", KEY_MIN_INTERESTING},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"KPASTERISK", KEY_KPASTERISK},
+      {(char*)0}, {(char*)0},
+      {"F13", KEY_F13},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"BLUETOOTH", KEY_BLUETOOTH},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"F8", KEY_F8},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"FN_F3", KEY_FN_F3},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {"NEW", KEY_NEW},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0},
+      {"F17", KEY_F17},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"BREAK", KEY_BREAK},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0},
+      {"FN_F8", KEY_FN_F8},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0}, {(char*)0},
+      {(char*)0}, {(char*)0}, {(char*)0},
+      {"WWW", KEY_WWW}
+    };
+
+  if (len <= MAX_WORD_LENGTH && len >= MIN_WORD_LENGTH)
+    {
+      register int key = hash_input_names (str, len);
+
+      if (key <= MAX_HASH_VALUE && key >= 0)
+        {
+          register const char *s = wordlist[key].name;
+
+          if (s && (((unsigned char)*str ^ (unsigned char)*s) & ~32) == 0 && !gperf_case_strcmp (str, s))
+            return &wordlist[key];
+        }
+    }
+  return 0;
+}
diff --git a/tools/hal-setup-keymap.c b/tools/hal-setup-keymap.c
new file mode 100644
index 0000000..e9a6473
--- /dev/null
+++ b/tools/hal-setup-keymap.c
@@ -0,0 +1,154 @@
+/*
+ * Licensed under the GNU General Public License Version 2
+ *
+ * Copyright (C) 2007 Richard Hughes <richard at hughsie.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ * 02110-1301, USA.
+ */
+
+#ifdef HAVE_CONFIG_H
+#  include <config.h>
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <string.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <sys/ioctl.h>
+
+#include <linux/input.h>
+
+#include "libhal/libhal.h"
+#include "hal-setup-keymap-hash-name.h"
+
+static LibHalContext *ctx = NULL;
+static char* udi;
+
+static int
+evdev_open (const char *dev)
+{
+	int fd;
+
+	/* requires root privs */
+	fd = open (dev, O_RDWR);
+	if (fd < 0) {
+		printf ("hal-setup-keymap: failed to open('%s'): %s\n",
+			dev, strerror (errno));
+		return -1;
+	}
+
+	return fd;
+}
+
+static int
+evdev_set_keycode (int fd, int scancode, int keycode)
+{
+	int ret;
+	int codes[2];
+
+	codes[0] = scancode;
+	codes[1] = keycode;
+
+	ret = ioctl (fd, EVIOCSKEYCODE, codes);
+	if (ret < 0) {
+		printf ("hal-setup-keymap: failed to set scancode %x to keycode %d: %s",
+			scancode, keycode, strerror(errno));
+		return -1;
+	}
+
+	return 0;
+}
+
+int
+main (int argc, char **argv)
+{
+	char **keymap_list;
+	int i = 0;
+	int fd;
+	unsigned int scancode = 0;
+	int keycode = 0;
+	char keyname[128];
+	int values;
+	char *device;
+	DBusError error;
+	const struct key *name;
+
+	udi = getenv ("UDI");
+	if (udi == NULL) {
+		printf ("hal-setup-keymap: Failed to get UDI");
+		return 1;
+	}
+	dbus_error_init (&error);
+	if ((ctx = libhal_ctx_init_direct (&error)) == NULL) {
+		printf ("hal-setup-keymap: Unable to initialise libhal context: %s", error.message);
+		return 1;
+	}
+
+	dbus_error_init (&error);
+	if (!libhal_device_addon_is_ready (ctx, udi, &error)) {
+		return 1;
+	}
+
+	/* get the string list data */
+	dbus_error_init (&error);
+	keymap_list = libhal_device_get_property_strlist (ctx, udi, "input.keymap.data", &error);
+	if (dbus_error_is_set (&error) == TRUE) {
+		printf ("hal-setup-keymap: Failed to get keymap list: '%s'", error.message);
+		return 1;
+	}
+
+	/* get the device */
+	device = libhal_device_get_property_string (ctx, udi, "input.device", &error);
+	if (dbus_error_is_set (&error) == TRUE) {
+		printf ("hal-setup-keymap: Failed to get input device list: '%s'", error.message);
+		return 1;
+	}
+
+	/* get a file descriptor to the device */
+	fd = evdev_open (device);
+	if (fd < 0) {
+		printf ("hal-setup-keymap: Could not open device");
+		return 1;
+	}
+
+	/* add each of the keys */
+	do {
+		values = sscanf (keymap_list[i], "%x:%s", &scancode, keyname);
+		if (values == 2) {
+			/* use gperf as it's really quick */
+			name = lookup_key (keyname, strlen(keyname));
+			if (name != NULL) {
+				keycode = name->id;
+				printf ("hal-setup-keymap: parsed %s to (%x, %i)",
+					keymap_list[i], scancode, keycode);
+				evdev_set_keycode (fd, scancode, keycode);
+			} else {
+				printf ("hal-setup-keymap: failed to find key '%s'", keyname);
+			}
+		} else {
+			printf ("hal-setup-keymap: Failed to parse %s", keymap_list[i]);
+		}
+	} while (keymap_list[i++] != NULL);
+
+	libhal_free_string_array (keymap_list);
+	close (fd);
+
+	/* we do not have to poll anything, so exit */
+	return 0;
+}
+


More information about the hal-commit mailing list