On a system running embedded linux I have a device connected to a rotary encoded (/dev/input/rotary). Now I'm trying to mimick such a device on a desktop by using
uinput, but I'm having trouble with the most basic test.
My
writer of events looks like this (with error handling removed):
Code:
int main(int ac, char **av)
{
int fd = open("/dev/uinput", O_WRONLY | O_NONBLOCK);
int ret = ioctl(fd, UI_SET_EVBIT, EV_ABS);
ret = ioctl(fd, UI_SET_ABSBIT, ABS_X);
struct uinput_user_dev uidev = {0};
snprintf(uidev.name, UINPUT_MAX_NAME_SIZE, "uinput-rotary");
uidev.absmin[ABS_X] = 0;
uidev.absmax[ABS_X] = 255;
ret = write(fd, &uidev, sizeof(uidev));
ret = ioctl(fd, UI_DEV_CREATE);
struct input_event ev = {0};
ev.type = EV_ABS;
ev.code = ABS_X;
ev.value = 42;
ret = write(fd, &ev, sizeof(ev));
getchar();
ret = ioctl(fd, UI_DEV_DESTROY);
return EXIT_SUCCESS;
}
The
reader of events looks this (also with error handling removed):
Code:
int main(int ac, char **av)
{
int fd = open(av[1], O_RDONLY);
char name[256] = "unknown";
ioctl(fd, EVIOCGNAME(sizeof(name)), name);
printf("reading from %s\n", name);
struct input_event ev = {0};
int ret = read(fd, &ev, sizeof(ev));
printf("Read an event! %i\n", ret);
printf("ev.time.tv_sec: %li\n", ev.time.tv_sec);
printf("ev.time.tv_usec: %li\n", ev.time.tv_usec);
printf("ev.type: %hi\n", ev.type);
printf("ev.code: %hi\n", ev.code);
printf("ev.value: %li\n", ev.value);
return EXIT_SUCCESS;
}
The output from the
reader is not at all what I expected:
Code:
% ./reader /dev/input/js0
reading from unknown
Read an event! 8
ev.time.tv_sec: 36732490196071166
ev.time.tv_usec: 0
ev.type: 0
ev.code: 0
ev.value: 0
The
reader seems to work on other inputs, I've tried it on the keyboard:
Code:
% sudo ./reader /dev/input/by-path/platform-i8042-serio-0-event-kbd
reading from AT Translated Set 2 keyboard
Yay! Read an event! 24
ev.time.tv_sec: 1414918317
ev.time.tv_usec: 328181
ev.type: 4
ev.code: 4
ev.value: 28
So, what am I missing in my usage of uinput?