I’ve been playing with hidd and an Apple wireless keyboard (secC). I’m toying with the notion of making my cell phone behave like a HID device. Interestingly, I found Peter Klauser’s bthid project, which basically does the dirty work of connecting to a Bluetooth HID device and sending the keystrokes on to the kernel. It uses the uinput kernel module, while the more widely used BlueZ Linux Bluetooth suite uses a module called evdev, presumably meaning “event device.”
There really isn’t much to the bthid-0.10, which is encouraging, because I think the behavior of the HID device itself is even less complex. Well, all the circuitry inside a wireless keyboard is complex, but, assuming I have a mobile phone that has a Bluetooth stack already, the additional workload is minimal.
And what about going the other direction? Here is a really nice program I found that allows any HID-compliant Bluetooth keyboard to talk to a mobile phone. I’ve only tried the demo version, which is sufficiently limited to not actually be useful, but I am seriously considering purchasing the full version.
Update: I got to hacking on the out.c file from bthid-0.10:
This page helped me greatly.
My goal was to generate keyboard events from a program. The simplest way I’ve found to do this is through the uinput kernel module, since it just exposes a file interface at /dev/input/uinput. So apparently uinput doesn’t really want the raw scan codes from the keyboard. It wants the key codes as defined in /usr/src/linux/include/linux/input.h. This makes me happy, actually, because they’re all defined in one place and it’s fairly straightforward.
The out_event() function in out.c takes 3 parameters:
Prototype: out_event (int evt, int which, int amount);
evt is one of either EV_KEY, EV_REL, or EV_ABS (and perhaps others, but I don’t care about them right now), for keyboard, relative movement, and absolute movement. I only care about keyboard (for now anyways).
which takes a key code as defined in input.h, and amount is 1 for press, 0 for release.
Thus, this does an `ls`:
out_event(EV_KEY, KEY_L, 1);
out_event(EV_KEY, KEY_L, 0);
out_event(EV_KEY, KEY_S, 1);
out_event(EV_KEY, KEY_S, 0);
out_event(EV_KEY, KEY_ENTER, 1);
out_event(EV_KEY, KEY_ENTER, 0);
And this does an `lS`:
out_event(EV_KEY, KEY_L, 1);
out_event(EV_KEY, KEY_L, 0);
out_event(EV_KEY, KEY_LEFTSHIFT, 1);
out_event(EV_KEY, KEY_S, 1);
out_event(EV_KEY, KEY_S, 0);
out_event(EV_KEY, KEY_LEFTSHIFT, 0);
out_event(EV_KEY, KEY_ENTER, 1);
out_event(EV_KEY, KEY_ENTER, 0);