OpenHarmony开发者论坛

标题: 【SUBJECT技术】探索 OpenHarmony libudev 设备热插拔机制 [打印本页]

作者: 诚迈_雨哥    时间: 2024-1-28 16:34
标题: 【SUBJECT技术】探索 OpenHarmony libudev 设备热插拔机制
[md]# 一、多模输入子系统设备热插拔事件来源

当前多模输入子系统处理设备热插拔事件的过程如图所示

![wps1.png](https://forums-obs.openharmony.c ... rrsivoxumyv3m0v.png "wps1.png")

现有多模输入子系统框架中,设备原始输入事件要经由libinput处理,封装成libinput的事件类型。多模输入子系统接收并处理libinput封装的事件。特别地,libinput依赖udev获得输入设备热插拔事件的通知。udev将监听热插拔事件、读取热插拔的设备信息,连同枚举已加载设备等接口实现封装成libudev共享库。libinput通过libudev封装的这些功能接口与udev通信,因而在编译时多模输入模块需要链接到libudev。


libinput依赖的两个关键路径是设备节点“/dev/input/<devnode>”和设备系统路径“/sys/class/input/<devnode>”。系统路径可以通过设备节点关联得到。通过设备节点可获得设备支持的事件和属性,以及接收和发送输入事件。通过系统路径可以获得设备的详细信息。


libinput依赖设备能力标记来分设备类型进行事件处理。这些标记是由udevd通过应用配置的规则计算得到的。


总结下来有几个关键点:
(1)libudev是在eudev项目中实现的。
(2)多模输入子系统从udevd获知输入设备热插拔,而设备节点由ueventd创建。
(3)多模输入子系统依赖udev提供的信息包括:输入设备热插拔通知;输入设备节点路径;输入设备的能力标记。udev支持广泛的设备类型,为此定义了一整套复杂的规则来处理设备热插拔事件。多模输入子系统只支持输入设备,我们可以通过简单的逻辑来获取这些信息。

# 二、判断设备类型

不同的输入设备支持不同的输入事件和属性的组合。

## 2.1 如触摸屏支持的事件

```cpp
  Discriminator:eviceType::TOUCHSCREEN, {
      .eventTypes {
        EV_KEY,
        EV_ABS,
      },
      .keys {
        BTN_TOUCH,
      },
      .abs {
        ABS_MT_TOUCH_MAJOR,
        ABS_MT_TOUCH_MINOR,
        ABS_MT_POSITION_X,
        ABS_MT_POSITION_Y,
        ABS_MT_TRACKING_ID,
        ABS_MT_PRESSURE,
        ......
      },
      .properties {
        INPUT_PROP_DIRECT,
      },
    }
```

## 2.2 鼠标支持的输入事件和属性

```cpp
Discriminator:eviceType::MOUSE, {
      .eventTypes {
        EV_KEY,
        EV_REL,
      },
      .keys {
        BTN_LEFT,
        BTN_RIGHT,
        BTN_MIDDLE
      },
      .rels {
        REL_X,
        REL_Y,
        REL_WHEEL
      }
    },
```

## 2.3 键盘支持的输入事件和属性

```cpp
Discriminator:eviceType::KEYBOARD,
    {
      .eventTypes {
        EV_KEY,
      },
      .keys {
        KEY_1, KEY_2, KEY_3, KEY_4, KEY_5, KEY_6, KEY_7, KEY_8, KEY_9,
        KEY_0, KEY_MINUS, KEY_EQUAL, KEY_BACKSPACE, KEY_TAB, KEY_Q,
        KEY_W, KEY_E, KEY_R, KEY_T, KEY_Y, KEY_U, KEY_I,
        KEY_O, KEY_P, KEY_LEFTBRACE, KEY_RIGHTBRACE,
        KEY_ENTER, KEY_LEFTCTRL, KEY_A, KEY_S, KEY_D, KEY_F,
        KEY_G, KEY_H, KEY_J, KEY_K, KEY_L, KEY_SEMICOLON,
        KEY_LEFTSHIFT, KEY_BACKSLASH, KEY_Z, KEY_X,
        KEY_C, KEY_V, KEY_B, KEY_N, KEY_M, KEY_COMMA, KEY_DOT,
        KEY_SLASH, KY_RIGHTSHIFT, KEY_LEFTALT, KEY_SPACE,
        KEY_CAPSLOCK, KEY_F1, KEY_F2, KEY_F3, KEY_F4, KEY_F5, KEY_F6,
        KEY_F7, KEY_F8, KEY_F9, KEY_F10, KEY_NUMLOCK,
        KEY_SCROLLLOCK, KEY_KP7, KEY_KP8, KEY_KP9, KEY_KPMINUS,
        KEY_KP4, KEY_KP5, KEY_KP6, KEY_KPPLUS, KEY_KP1, KEY_KP2,
        KEY_KP3, KEY_KP0, KEY_KPDOT, KEY_F11, KEY_F12, ......
      },
    },
```

# 三、主要程序处理逻辑

## 3.1 libinput初始化

![wps3.png](https://forums-obs.openharmony.c ... fv2pqxc2wwvaow0.png "wps3.png")

## 3.2 热插拔事件处理

![wps4.png](https://forums-obs.openharmony.c ... o3ohwnw0mjzgvbz.png "wps4.png")

## 3.3 模块结构

![wps5.png](https://forums-obs.openharmony.c ... 3mes0jaywn4dyi7.png "wps5.png")

## 3.4 接口列表struct udev;

# 四、udevd进程

## 4.1 udevd是一个守护进程

udevd启动时通过netlink scoket监听内核通知的设备热插拔事件:
src/udev/udevd.c:main()

![wps14.png](https://forums-obs.openharmony.c ... d7up09f8b2m706b.png "wps14.png")

当接收到内核发出的设备热插拔事件时,udevd将事件加入事件队列,启动工作进程处理事件:
src/udev/udevd.c:main()

![wps15.png](https://forums-obs.openharmony.c ... vbllvsawpaalvah.png "wps15.png")

工作进程处理热插拔事件,应用配置的规则,执行处理例程,然后将处理后的事件转发给libudev事件监听者(libinput):
src/udev/udevd.c:worker_spawn()

![wps16.jpg](https://forums-obs.openharmony.c ... whmwaswme855ve3.jpg "wps16.jpg")

libinput依赖udevd处理过的事件进行设备识别。如果去掉规则匹配部分的逻辑,测试时libinput不能正常识别设备。参考日志:

![wps17.png](https://forums-obs.openharmony.c ... xpa6bhaa9za93bb.png "wps17.png")

![wps18.png](https://forums-obs.openharmony.c ... u45g2anllftlprr.png "wps18.png")

![wps19.png](https://forums-obs.openharmony.c ... 23vfvpqvmvv5q2p.png "wps19.png")

![wps20.png](https://forums-obs.openharmony.c ... i2j6b261ucc6pyj.png "wps20.png")



## 4.2 udevd规则处理逻辑

udevd启动时会遍历预定的目录,寻找规则配置文件。udevd逐个解析每个规则配置文件,形成一个规则项的数组。单个配置文件解析得到的规则项是按序连续排列的,其中第一项(如下图的蓝色项)记录了一些从相应规则配置文件解析得到的规则项的信息,包括规则项的个数等。从该配置文件解析得到的规则项紧接着按规则的类型顺序排列。这些规则项可分为两类,一类用来做匹配,另一类指示执行的动作。如下图所示:

![wps21.png](https://forums-obs.openharmony.c ... vzc9ee8z2e4s21d.png "wps21.png")

应用规则时,单个规则配置文件中的所有规则项是作为一个整体考虑的。设备的属性应匹配所有的匹配项,才能应用后面的动作。

## 4.3 UDEV鼠标标记

![wps30.png](https://forums-obs.openharmony.c ... 66skiq9g9vyze9y.png "wps30.png")

# 五、ueventd进程

## 5.1 ueventd是一个守护进程

它通过netlink scoket监听内核生成的uevent消息。当ueventd接收到uevent消息时,采取适当的动作来处理。典型的场景是当有设备热插/拔时,内核发送uevent事件通知用户端;ueventd接收到此uevent事件,执行如创建/移除设备节点的动作。
系统正常启动后,ueventd会超时退出。当有设备热插拔事件上报时,如果udevd进程未运行,则系统会拉起ueventd进程处理事件,创建设备节点。
OpenHarmony的ueventd进程的代码在“/base/startup/init_lite/ueventd/”目录中。系统启动后,ueventd通过netlink scoket监听内核发送的输入设备热插拔事件。

## 5.2 当前ueventd的实现支持“input”子系统事件的处理

参考日志:

![wps31.png](https://forums-obs.openharmony.c ... kzazmazh97kidih.png "wps31.png")

## 5.3 ueventd可接收并处理设备热插拔事件

测试时加载了两个虚拟触摸屏设备,uevent响应并创建了设备节点,ueventd输出日志:

![wps32.png](https://forums-obs.openharmony.c ... fnu73ui7f7nnkne.png "wps32.png")

## 5.4 测试插入键盘,uevent创建了设备节点

参考日志:

![wps33.png](https://forums-obs.openharmony.c ... 7lyjh7rgo9gv9lo.png "wps33.png")

## 5.5 测试插入鼠标,uevent创建了设备节点

![wps34.png](https://forums-obs.openharmony.c ... 7cco0cwafilm1ox.png "wps34.png")

## 5.6 ueventd的日志输出

![wps35.png](https://forums-obs.openharmony.c ... bszfxs683bzlffp.png "wps35.png")

## 5.7 一个问题是ueventd有监听超时时间设置

设备启动后uevent进程因超时而结束运行。如果去除ueventd的超时设置,ueventd则保持运行:

![wps36.png](https://forums-obs.openharmony.c ... reyxphmraim5c8q.png "wps36.png")

## 5.8 另一个问题是ueventd的功能简单

未提供事件通知的接口和设备信息获取的接口,如果多模依赖ueventd实现设备热插拔,则需要增加实现这些接口。

# 六、各类型输入设备支持的事件和属性

## 6.1 键盘支持的事件类型和属性

![wps37.jpg](https://forums-obs.openharmony.c ... xyx5ezr75t47zq4.jpg "wps37.jpg")

![wps38.jpg](https://forums-obs.openharmony.c ... kerk8ee0eed9j9r.jpg "wps38.jpg")

![wps39.jpg](https://forums-obs.openharmony.c ... 2yp3tfu9anc223e.jpg "wps39.jpg")

![wps40.jpg](https://forums-obs.openharmony.c ... 3g718j74zj3pyy3.jpg "wps40.jpg")

![wps41.jpg](https://forums-obs.openharmony.c ... z8ix8g8iemwcgkg.jpg "wps41.jpg")

![wps42.jpg](https://forums-obs.openharmony.c ... lep6pblxbxxz6pl.jpg "wps42.jpg")

## 6.2 鼠标支持的事件类型和属性

![wps43.jpg](https://forums-obs.openharmony.c ... 9kqf3nof9t9f3ok.jpg "wps43.jpg")

## 6.3 触摸屏支持的事件类型和属性

![wps44.jpg](https://forums-obs.openharmony.c ... wbi7buak7k21vz7.jpg "wps44.jpg")

![wps45.jpg](https://forums-obs.openharmony.c ... z8lzpei87bieiin.jpg "wps45.jpg")

## 6.4 数位板支持的事件类型和属性

![wps46.jpg](https://forums-obs.openharmony.c ... d3la0v7i7pppall.jpg "wps46.jpg")

![wps47.jpg](https://forums-obs.openharmony.c ... jpqjglq1yggyv2c.jpg "wps47.jpg")

![wps48.jpg](https://forums-obs.openharmony.c ... sogkm8cztut8v4y.jpg "wps48.jpg")

![wps49.jpg](https://forums-obs.openharmony.c ... yyyl08l80hy80sm.jpg "wps49.jpg")

![wps50.jpg](https://forums-obs.openharmony.c ... mb2gllmiizlyxxo.jpg "wps50.jpg")

![wps51.jpg](https://forums-obs.openharmony.c ... 5oruwm0uvl75w3d.jpg "wps51.jpg")

![wps51.jpg](https://forums-obs.openharmony.c ... cneym99ncnjnuyc.jpg "wps51.jpg")

![wps52.jpg](https://forums-obs.openharmony.c ... cljb252b3d2du41.jpg "wps52.jpg")

![wps53.jpg](https://forums-obs.openharmony.c ... b77kkoty17bo0xl.jpg "wps53.jpg")

![wps54.jpg](https://forums-obs.openharmony.c ... 5jl7ll7gm1377so.jpg "wps54.jpg")

![wps55.jpg](https://forums-obs.openharmony.c ... 2dqdui2tg5g6dwu.jpg "wps55.jpg")

![wps56.jpg](https://forums-obs.openharmony.c ... v9qpoogidiaci5b.jpg "wps56.jpg")

![wps57.jpg](https://forums-obs.openharmony.c ... cegzcgdduzfkh7f.jpg "wps57.jpg")

![wps58.jpg](https://forums-obs.openharmony.c ... 09z51rr4isb0eg0.jpg "wps58.jpg")

## 6.5 手写笔支持的事件类型和属性

![wps59.jpg](https://forums-obs.openharmony.c ... dstcrccpss6c1pa.jpg "wps59.jpg")

![wps60.jpg](https://forums-obs.openharmony.c ... jx2eb3m2tembm1s.jpg "wps60.jpg")

![wps61.jpg](https://forums-obs.openharmony.c ... 3na3m43hsmr4lp2.jpg "wps61.jpg")

![wps62.jpg](https://forums-obs.openharmony.c ... 36o7t22khti5kt6.jpg "wps62.jpg")

![wps63.jpg](https://forums-obs.openharmony.c ... 5pdppy9zkcc9685.jpg "wps63.jpg")
[/md]




欢迎光临 OpenHarmony开发者论坛 (https://forums.openharmony.cn/) Powered by Discuz! X3.5