Android framework Input 之getevent详解

容阳焱
2023-12-01

使用详解

xxxxxxxx:/ # getevent -h
Usage: getevent [-t] [-n] [-s switchmask] [-S] [-v [mask]] [-d] [-p] [-i] [-l] [-q] [-c count] [-r] [device]
    -t: show time stamps -显示事件的发生时间
    -n: don't print newlines
    -s: print switch states for given bits
    -S: print all switch states
    -v: verbosity mask (errs=1, dev=2, name=4, info=8, vers=16, pos. events=32, props=64)
    -d: show HID descriptor, if available
    -p: show possible events (errs, dev, name, pos. events)
    -i: show all device info and possible events
    -l: label event types and names in plain text -这里表示要把event事件类型名字打印出来
    -q: quiet (clear verbosity mask)
    -c: print given number of events then exit
    -r: print rate events are received  -显示一下接受事件速率

常用的就是getevent -lrt

xxxx:/ # getevent -lrt
add device 1: /dev/input/event0
  name:     "ACCDET"
add device 2: /dev/input/event7
  name:     "ln4912"
add device 3: /dev/input/event10
  name:     "mtk-tpd"
add device 4: /dev/input/event6
  name:     "ln4913"
add device 5: /dev/input/event2
  name:     "dbmdx4"
add device 6: /dev/input/event8
  name:     "fts_ts"
add device 7: /dev/input/event4
  name:     "als"
add device 8: /dev/input/event3
  name:     "tcs3408"
add device 9: /dev/input/event1
  name:     "mtk-kpd"
add device 10: /dev/input/event5
  name:     "flicker"
add device 11: /dev/input/event9
  name:     "fts_ts,pen"
[     104.141089] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000000  //代表第一个手指,其实第一个也可以没有,有的机器就第一次0是没有这个slot 
[     104.141089] /dev/input/event8: EV_ABS       ABS_MT_TRACKING_ID   00000007 //第一个手指对应的TRACKING_ID  
[     104.141089] /dev/input/event8: EV_ABS       ABS_MT_TOUCH_MAJOR   00000040 //第一个手指按下时接触屏幕的椭圆长轴。
[     104.141089] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    0000044d //第一个手指按下的X轴坐标
[     104.141089] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    0000020b //第一个手指按下的y轴坐标
[     104.141089] /dev/input/event8: EV_KEY       BTN_TOUCH            DOWN     //触摸按下
[     104.141089] /dev/input/event8: EV_SYN       SYN_REPORT           00000000 //第一个手指同步事件完
[     104.157111] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000001 //代表第二个手指
[     104.157111] /dev/input/event8: EV_ABS       ABS_MT_TRACKING_ID   00000008 //第二个手指对应的TRACKING_ID  
[     104.157111] /dev/input/event8: EV_ABS       ABS_MT_TOUCH_MAJOR   00000040 //第二个手指按下时接触屏幕的椭圆长轴。
[     104.157111] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    000005b5 //第二个手指按下的X轴坐标
[     104.157111] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    0000025e //第二个手指按下的y轴坐标
[     104.157111] /dev/input/event8: EV_SYN       SYN_REPORT           00000000 //第二个手指同步事件完            rate 62
[     104.189299] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    000005b2
[     104.189299] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 31
[     104.199057] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000000
[     104.199057] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    0000044c
[     104.199057] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 102
[     104.206137] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    0000044a
[     104.206137] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    0000020c
[     104.206137] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000001
[     104.206137] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    000005af
[     104.206137] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    00000260
[     104.206137] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 141
[     104.214889] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000000
[     104.214889] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    00000443
[     104.214889] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    0000020f
[     104.214889] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000001
[     104.214889] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    000005aa
[     104.214889] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    00000262
[     104.214889] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 114
[     104.222955] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000000
[     104.222955] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    0000043e
[     104.222955] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    00000213
[     104.222955] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000001
[     104.222955] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    000005a1
[     104.222955] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    00000266
[     104.222955] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 123
[     104.231189] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000000
[     104.231189] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    00000436
[     104.231189] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    00000219
[     104.231189] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000001
[     104.231189] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    00000596
[     104.231189] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    0000026b
[     104.231189] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 121
[     104.239773] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000000
[     104.239773] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    0000042e
[     104.239773] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    0000021f
[     104.239773] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000001
[     104.239773] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    00000588
[     104.239773] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    00000271
[     104.239773] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 116
[     104.248354] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000000
[     104.248354] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    00000424
[     104.248354] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    00000226
[     104.248354] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000001
[     104.248354] /dev/input/event8: EV_ABS       ABS_MT_POSITION_X    00000573
[     104.248354] /dev/input/event8: EV_ABS       ABS_MT_POSITION_Y    00000279
[     104.248354] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 116
[     104.260568] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000000 //第一个手指
[     104.260568] /dev/input/event8: EV_ABS       ABS_MT_TRACKING_ID   ffffffff //TRACKING_ID为-1,代表第一个手指抬起消失
[     104.260568] /dev/input/event8: EV_ABS       ABS_MT_SLOT          00000001 //第二个手指
[     104.260568] /dev/input/event8: EV_ABS       ABS_MT_TRACKING_ID   ffffffff //TRACKING_ID为-1,代表第二个手指抬起消失
[     104.260568] /dev/input/event8: EV_KEY       BTN_TOUCH            UP       //触摸抬起
[     104.260568] /dev/input/event8: EV_SYN       SYN_REPORT           00000000             rate 81

[ 112248.432102] /dev/input/event8: EV_SYN SYN_REPORT 00000000 rate 117

时间 具体节点文件名 事件类型 事件code 事件value rate接收速率

事件类型

1.EV_SYN
同步事件完,在事件开始或完成会有
对应的code
0004:代表一个事件开始(不必要,不一定有显示)
0005:代表一个事件开始(不必要,不一定有显示)
SYN_REPORT:代表一个事件的结束 (必要)

2.EV_ABS
事件的一种绝对坐标类型
对应code
2.0 ABS_MT_SLOT
本质代表者不同手指,它的value代表手指id
2.1 ABS_MT_TRACKING_ID

类型B特有的,实际上,每个slot会和一个ID相对应,一个非负数的表示一次接触,-1表示这是一个无用的slot(或者理解为一次接触的结束) 。无论在接触的类型相对应的slot发生了改变,驱动都应该通过改变这个值来使这个slot失效。并且下一次触摸的ID值会是这次的值加1。

2.2 ABS_MT_POSITION_X,ABS_MT_POSITION_Y

相对于屏幕中心的x,y坐标。

2.3 ABS_MT_TOUCH_MAJOR

接触部分的长轴长度。相当于椭圆的长轴。

2.4 ABS_MT_TOUCH_MINOR

接触部分的短轴长度。相当于椭圆的短轴。

2.5 ABS_MT_PRESSURE
代表按下压力,有的设备不一定有

3.EV_KEY
事件的一种类型。表示是按键(不仅仅指的物理按键也包括TOUCH)事件
对应code
3.1 BTN_TOUCH

触碰按键。其值是DOWN或者UP

3.2 BTN_TOOL_FINGER

按键的是finger,并且其值也是DOWN或者UP,不一定存在

源码解剖

android-12.0.0_r28/system/core/toolbox/getevent.c

int getevent_main(int argc, char *argv[])
{
    ...
    const char *device = NULL;
    const char *device_path = "/dev/input";

    /* disable buffering on stdout */
    setbuf(stdout, NULL);

    ....

    if (optind + 1 == argc) {
        device = argv[optind];
        optind++;
    }
    if (optind != argc) {
        usage(argv[0]);
        exit(1);
    }
    // 通过poll机制监听文件
    nfds = 1;
    ufds = calloc(1, sizeof(ufds[0]));
    ufds[0].fd = inotify_init();
    ufds[0].events = POLLIN;
    //device 就是有没有带文件路径,比如getevent -lrt /dev/input/event8
    if(device) {
        if(!print_flags_set)
            print_flags |= PRINT_DEVICE_ERRORS;
        res = open_device(device, print_flags);
        if(res < 0) {
            return 1;
        }
    } else {
        if(!print_flags_set)
            print_flags |= PRINT_DEVICE_ERRORS | PRINT_DEVICE | PRINT_DEVICE_NAME;
        print_device = 1;
        //监听device_path目录(/dev/input/)
		res = inotify_add_watch(ufds[0].fd, device_path, IN_DELETE | IN_CREATE);
        if(res < 0) {
            fprintf(stderr, "could not add watch for %s, %s\n", device_path, strerror(errno));
            return 1;
        }
        res = scan_dir(device_path, print_flags);
        if(res < 0) {
            fprintf(stderr, "scan dir failed for %s\n", device_path);
            return 1;
        }
    }

    ...

    if(dont_block)
        return 0;

    while(1) {
        //int pollres =
        poll(ufds, nfds, -1);
        //printf("poll %d, returned %d\n", nfds, pollres);
        if(ufds[0].revents & POLLIN) {
            read_notify(device_path, ufds[0].fd, print_flags);
        }
        for(i = 1; i < nfds; i++) {
            if(ufds[i].revents) {
                if(ufds[i].revents & POLLIN) {
                    res = read(ufds[i].fd, &event, sizeof(event));
                    if(res < (int)sizeof(event)) {
                        fprintf(stderr, "could not get event\n");
                        return 1;
                    }
                    if(get_time) {
                        printf("[%8ld.%06ld] ", event.time.tv_sec, event.time.tv_usec);
                    }
                    if(print_device)
                        printf("%s: ", device_names[i]);
                    print_event(event.type, event.code, event.value, print_flags);
                    if(sync_rate && event.type == 0 && event.code == 0) {
                        int64_t now = event.time.tv_sec * 1000000LL + event.time.tv_usec;
                        if(last_sync_time)
                            printf(" rate %lld", 1000000LL / (now - last_sync_time));
                        last_sync_time = now;
                    }
                    printf("%s", newline);
                    if(event_count && --event_count == 0)
                        return 0;
                }
            }
        }
    }

    return 0;
}

static int scan_dir(const char *dirname, int print_flags)
{
    char devname[PATH_MAX];
    char *filename;
    DIR *dir;
    struct dirent *de;
    dir = opendir(dirname);
    if(dir == NULL)
        return -1;
    strcpy(devname, dirname);
    filename = devname + strlen(devname);
    *filename++ = '/';
    while((de = readdir(dir))) {
        if(de->d_name[0] == '.' &&
           (de->d_name[1] == '\0' ||
            (de->d_name[1] == '.' && de->d_name[2] == '\0')))
            continue;
        strcpy(filename, de->d_name);
        open_device(devname, print_flags);
    }
    closedir(dir);
    return 0;
}

static int open_device(const char *device, int print_flags)
{
    ....

    ufds[nfds].fd = fd;
    ufds[nfds].events = POLLIN;
    device_names[nfds] = strdup(device);
    nfds++;

    return 0;
}

 类似资料: