반응형

출처 : http://www.mail-archive.com/linux-input@vger.kernel.org/msg00063.html



Sending simulated mouse events using uinput



Greetings oh Linux input wranglers,

At Nuvation we are building a driver for multiple input devices, all of which 
need to appear as mouse events in userland.  We've tried several approaches 
without any good results.  Lately I've been looking at the uinput module, 
especially after finding an article in January 2007 Dashboard about how to do 
it:
   www.einfochips.com/download/dash_jan_tip.pdf

I made a slightly modified version of the sample code from that article.  I 
enabled uinput, verified that it is in place, did chmod a+rw on it so I could 
open it for writing, and compiled this:

===================================

#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <linux/input.h>
#include <linux/uinput.h>
#include <sys/time.h>
#include <unistd.h>

// Test the uinput module

struct uinput_user_dev   uinp;
struct input_event       event;

int main(void) {

            int ufile, retcode, i;

            ufile = open("/dev/input/uinput", O_WRONLY | O_NDELAY );
            printf("open /dev/input/uinput returned %d.\n", ufile);
            if (ufile == 0) {
                        printf("Could not open uinput.\n");
                        return -1;
            }

            memset(&uinp, 0, sizeof(uinp));
            strncpy(uinp.name, "simulated mouse", 20);
            uinp.id.version = 4;
            uinp.id.bustype = BUS_USB;

            ioctl(ufile, UI_SET_EVBIT, EV_KEY);
            ioctl(ufile, UI_SET_EVBIT, EV_REL);
            ioctl(ufile, UI_SET_RELBIT, REL_X);
            ioctl(ufile, UI_SET_RELBIT, REL_Y);

            for (i=0; i<256; i++) {
                        ioctl(ufile, UI_SET_KEYBIT, i);
            }

            ioctl(ufile, UI_SET_KEYBIT, BTN_MOUSE);

            // create input device in input subsystem
            retcode = write(ufile, &uinp, sizeof(uinp));
            printf("First write returned %d.\n", retcode);

            retcode = (ioctl(ufile, UI_DEV_CREATE));
            printf("ioctl UI_DEV_CREATE returned %d.\n", retcode);
            if (retcode) {
                        printf("Error create uinput device %d.\n", retcode);
                        return -1;
            }

            // NOW DO STUFF !!!!

            for (i=0; i<100; i++) {

                        struct timeval tv1;

                        // move pointer upleft by 5 pixels
                        memset(&event, 0, sizeof(event));
                        gettimeofday(&event.time, NULL);
                        event.type = EV_REL;
                        event.code = REL_X;
                        event.value = -5;
                        write(ufile, &event, sizeof(event));
            
                        memset(&event, 0, sizeof(event));
                        gettimeofday(&event.time, NULL);
                        event.type = EV_REL;
                        event.code = REL_Y;
                        event.value = -5;
                        write(ufile, &event, sizeof(event));
            
                        memset(&event, 0, sizeof(event));
                        gettimeofday(&event.time, NULL);
                        event.type = EV_SYN;
                        event.code = SYN_REPORT;
                        event.value = 0;
                        write(ufile, &event, sizeof(event));

                        // wait just a moment
                        do { gettimeofday(&tv1, NULL); } while ((tv1.tv_usec & 
0x3FFF) != 0);
                        do { gettimeofday(&tv1, NULL); } while ((tv1.tv_usec & 
0x3FFF) == 0);
            }

            // destroy the device
            ioctl(ufile, UI_DEV_DESTROY);

            close(ufile);

}

==============

As I understand it, this ought to cause the mouse to move slowly upleft for a 
few seconds - but nothing happens!  It is not clear to me what is wrong.

The output on the command line is thus:

[EMAIL PROTECTED] uinputtest]$ gcc uinputtest.c
[EMAIL PROTECTED] uinputtest]$ ./a.out
open /dev/input/uinput returned 3.
First write returned 1116.
ioctl UI_DEV_CREATE returned 0.
[EMAIL PROTECTED] uinputtest]$

I am running Fedora on a VM (using VMWare Player) on a Windows XP machine.  
Here is /etc/X11/xorg.conf:



# Xorg configuration created by system-config-display

Section "ServerLayout"
            Identifier     "single head configuration"
            Screen      0  "Screen0" 0 0
            InputDevice    "Keyboard0" "CoreKeyboard"
            InputDevice    "VMMouse" "CorePointer"
EndSection

Section "InputDevice"
            Identifier  "Keyboard0"
            Driver      "kbd"
            Option     "XkbModel" "pc105"
            Option     "XkbLayout" "us"
EndSection

Section "InputDevice"
            Identifier  "VMMouse"
            Driver      "vmmouse"
            Option     "Device" "/dev/input/mice"
            Option     "Emulate3Buttons" "yes"
EndSection

Section "Monitor"
            Identifier   "Monitor0"
            ModelName    "LCD Panel 1680x1050"
            HorizSync    31.5 - 90.0
            VertRefresh  59.9 - 60.1
            Option     "dpms"
EndSection

Section "Device"
            Identifier  "Videocard0"
            Driver      "vmware"
EndSection

Section "Screen"
            Identifier "Screen0"
            Device     "Videocard0"
            Monitor    "Monitor0"
            DefaultDepth     24
            SubSection "Display"
                        Viewport   0 0
                        Depth     24
            EndSubSection
EndSection



Can anyone offer some advice?  Are we forgetting something terribly obvious?  
Is the fact of running under a VM somehow messing us up?

Thanks, people.  I'm new to Linux - it's great to find out what a large group 
of humans are actively supporting it.

Looking forward to any replies,

Nick Turner
Design Engineer
Nuvation, inc.
San Jose, CA
408-228-5580 x258

-
To unsubscribe from this list: send the line "unsubscribe linux-input" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html

반응형
Posted by Real_G