Android Sensor 框架
一图胜千言

RK sensor
不同平台在 kernel 层的实现不一样,RK、MTK、高通 三家都有自己的框架。下文只介绍 RK sensor 在 kernel 层的框架。
根据产品形态的不同,MTK 和高通的 sensor 框架比较像,因为做的是手机,需要低功耗,所以 sensor 不会挂在 kernel,而是放在一个单片机中跑,需要数据的时候通过核间通信报给 kernel,kernel 再往上报。而 RK 平台是把所有的传感器直接挂在 kernel,不考虑低功耗场景。
RK 平台 Sensor 代码路径:/kernel/drivers/input/sensors/

sensor-dev.c 是核心代码,整合了不同类型的 sensor,包括 accel, gyro, lsensor, psensor, compass 等。封装具体 sensor 驱动的申请、注册函数。
sensor-i2c.c 封装 i2c 接口函数。
sensor-i2c.c 和 sensor-dev.c 组成 RK sensor core。由它来支撑具体 sensor 的活动并回调具体 sensor 驱动提供的钩子函数。
RK3399
博主手里有一块 RK3399 的板子,带的 sensor 原理图如下:



从 dts 看,他们挂在一路 I2C4,速率是 400Khz。对于要求更高的产品来讲,建议 accgyro 单独使用一路 SPI,其他的 sensor 可以共用一路 I2C。
i2c@ff3d0000 {
compatible = "rockchip,rk3399-i2c";
reg = <0x0 0xff3d0000 0x0 0x1000>;
clocks = <0x2f 0xa 0x2f 0x1c>;
clock-names = "i2c", "pclk";
interrupts = <0x0 0x38 0x4 0x0>;
pinctrl-names = "default";
pinctrl-0 = <0x80>;
#address-cells = <0x1>;
#size-cells = <0x0>;
status = "okay";
i2c-scl-rising-time-ns = <345>;
i2c-scl-falling-time-ns = <11>;
clock-frequency = <400000>;
phandle = <0x117>;
lsm330_accel@1e {
status = "okay";
compatible = "lsm330_acc";
pinctrl-names = "default";
pinctrl-0 = <0x81>;
reg = <0x1e>;
irq-gpio = <0x33 0x16 0x1>;
type = <0x2>;
irq_enable = <0x1>;
poll_delay_ms = <0x1e>;
power-off-in-suspend = <0x1>;
layout = <0x4>;
};
lsm330_gyro@6a {
status = "okay";
compatible = "lsm330_gyro";
pinctrl-names = "default";
pinctrl-0 = <0x82>;
reg = <0x6a>;
irq-gpio = <0x33 0x18 0x1>;
type = <0x4>;
irq_enable = <0x0>;
power-off-in-suspend = <0x1>;
poll_delay_ms = <0x1e>;
};
sensor@0f {
status = "okay";
compatible = "ak8963";
pinctrl-names = "default";
pinctrl-0 = <0x83>;
reg = <0xf>;
type = <0x3>;
irq-gpio = <0x33 0x0 0x1>;
irq_enable = <0x0>;
poll_delay_ms = <0x1e>;
layout = <0x3>;
};
sensor@10 {
status = "okay";
compatible = "capella,light_cm3218";
pinctrl-names = "default";
pinctrl-0 = <0x84>;
reg = <0x10>;
type = <0x5>;
irq-gpio = <0x85 0x18 0x2>;
irq_enable = <0x1>;
poll_delay_ms = <0x1e>;
};
};
Sensor driver 实现在 /drivers/input/sensors/,实现的也很简单,就是对 sensor IC 寄存器初始化后,读取数据,通过 input 子系统上报。
一般的嵌入式设备,都有加速度 acc,陀螺仪 gyro,光线传感器 als,磁力传感器 mag。
这里 lsm330 是 acc+gyro 二合一,cm32181 是 als,ak8963 是 mag,也叫电子罗盘 compass。这里缺少了距离传感器 ps,很多器件是 als+ps 二合一的,根据产品形态决定要不要加 ps。
RK 也没有提供虚拟 sensor,需要的话需要自己实现。虚拟 sensor 就是利用多个物理 sensor 的数据进行耦合,实现其他功能的 sensor。常见的虚拟 sensor 有计步器、抬手亮屏等。