[patch] add keymap data to make random laptop vendor keys work

Lennart Poettering mzuny at 0pointer.de
Mon Jun 4 07:33:29 PDT 2007


On Mon, 04.06.07 14:24, Richard Hughes (hughsient at gmail.com) wrote:

A few comments:

> +#include <stdio.h>
> +#include <stdlib.h>
> +#include <errno.h>
> +#include <string.h>
> +#include <fcntl.h>
> +#include <sys/ioctl.h>
> +
> +#include <linux/input.h>
> +#include <linux/kd.h>

No need to include "kd.h" if you use the linux input API.

> +static int
> +evdev_set_keycode (int fd, int scancode, int keycode)
> +{
> +	int ret;
> +	struct kbkeycode kb;
> +
> +	kb.keycode = keycode;
> +	kb.scancode = scancode;

Uh!

You have to pass an int[2] here, not a struct kbkeycode.

> +	/* add each of the keys */
> +	do {
> +		values = sscanf (keymap_list[i], "%x:%i", &scancode, &keycode);
> +		if (values == 2) {
> +			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 parse %s", keymap_list[i]);
> +		}
> +	} while (keymap_list[i++] != NULL);

Please do not use the numeric Linux keycodes directly for
this. Firstly, this is not portable. Secondly, this is not extensible,
since the Linux keycode space is mostly depleted already. Use the
names instead. Eventually the kernel guys might come up with a
completely new mapping thing again, to extend the code space.

In keyfuzz I use these Makefile lines for generating a static gperf hashtable
for translating these keycodes:

<snip>
keys.txt: input.h Makefile
          awk '/^#define.*KEY_/ { if ($$2 != "KEY_MAX") { print $$2 }
          }' < $< > $@

keys-from-name.gperf: keys.txt Makefile
                      awk 'BEGIN{ print "struct key { const char*
                      name; unsigned short id; };"; print
                      "%null-strings"; print "%%";} { print $$1 ", "
                      $$1 }' < $< > $@

keys-from-name.h: keys-from-name.gperf Makefile
                  gperf -t --ignore-case -N lookup_key -H
                  hash_key_name -p -C < $< > $@

keys-to-name.h: keys.txt Makefile
                awk 'BEGIN{ print "const char* const
                key_names[KEY_MAX] = { "} { print "[" $$1 "] = \"" $$1
                "\"," } END{print "};"}' < $< > $@
</snip>

Indenting borked. Get the original stuff from:

http://0pointer.de/cgi-bin/viewcvs.cgi/trunk/src/Makefile.am?rev=19&root=keyfuzz&view=auto

You can probably omit the keys-to-name part, as you only want to
translate keycodes to names and not vice versa.

> +    <!-- These are raw scancodes produced by the keyboard driver -->
> +    <match key="info.product" string="AT Translated Set 2 keyboard">
> +
> +      <match key="/org/freedesktop/Hal/devices/computer:system.hardware.vendor" prefix="LENOVO">
> +        <match key="/org/freedesktop/Hal/devices/computer:smbios.system.version" contains="3000">

There seems to be an implicit guarantee that atkb shows up in the HAL
device tree after DMI. Is that really guaranteed in all cases?

> +          <append key="input.keymap.data.linux" type="strlist">e016:238</append> <!-- Fn+F5 wireless	KEY_WLAN -->
> +          <append key="input.keymap.data.linux" type="strlist">e017:142</append> <!-- Fn+F4 suspend	KEY_SLEEP -->
> +          <append key="input.keymap.data.linux" type="strlist">e018:205</append> <!-- Fn+F12 hibernate	KEY_SUSPEND -->
> +          <append key="info.capabilities" type="strlist">input.keymap</append>
> +        </match>
> +      </match>
> +
> +    </match>
> +
> +    <!-- These are buttons synthesized in kernel drivers -->
> +    <match key="info.product" string="ThinkPad Extra Buttons">
> +      <match key="/org/freedesktop/Hal/devices/computer:system.hardware.vendor" prefix="LENOVO">
> +        <append key="input.keymap.data.linux" type="strlist">007f:152</append> <!-- thinkvantage	KEY_COFFEE -->
> +        <append key="info.capabilities" type="strlist">input.keymap</append>
> +      </match>
> +    </match>

One question here: Why don't the thinkpad kernel drivers contain the proper
mappings anyway? Why is there the need for additional remapping from userspace?

Lennart

-- 
Lennart Poettering                        Red Hat, Inc.
lennart [at] poettering [dot] net         ICQ# 11060553
http://0pointer.net/lennart/           GnuPG 0x1A015CC4


More information about the hal mailing list