1. 前言
本文主要讲的是rockchip的3568+gc2053,源码由rk提供。
2. 引入异步注册的原因
在soc中的视频处理一般由多个ip组成,比如cis_dphy、mipi_cis、isp、sensor等,甚至更多的ip, 这样就导致了v4l2的复杂性。在v4l2中的视频数据流是有方向和顺序的,因此在linux中引入了异步注册机制。异步注册的核心在于设备树引入port接口,在子设备中有一个或多个port接口,port接口就是子设备的纽带。
3. v4l2设备注册
在rk3568中包含4个设备:
isp-subdev:图像处理控制器,如3a处理,并将处理后的所得的参数反馈给sensor。
csi-subdev:mipi数据解析控制器。
cis2-dphy1: mipi数据硬件接收控制器。
gc2053: 外接的sensor,支持mipi输出。
连接方式:gc2053->csi2-dphy1->cis-subdev->isp-subdev
sensor以mipi方式传输到soc, soc通过mipi_dphy对数据进行接收,通过mipi_cis解析后并送往isp进行各种处理(ae、af、awb等)。
4. 设备树
&rkisp_vir0 {
status = "okay";
port {
#address-cells = <1>;
#size-cells = <0>;
isp0_in: endpoint@0 {
reg = <0>;
remote-endpoint = <&dphy1_out>;
};
};
};
&csi2_dphy1 {
status = "okay";
/*
* dphy1 only used for split mode,
* can be used concurrently with dphy2
* full mode and split mode are mutually exclusive
*/
ports {
#address-cells = <1>;
#size-cells = <0>;
port@0 {
reg = <0>;
#address-cells = <1>;
#size-cells = <0>;
dphy1_in: endpoint@1 {
reg = <1>;
remote-endpoint = <&gc2053_out>;
data-lanes = <1 2>;
};
};
port@1 {
reg = <1>;
#address-cells = <1>;
#size-cells = <0>;
dphy1_out: endpoint@1 {
reg = <1>;
remote-endpoint = <&isp0_in>;
};
};
};
};
&i2c2 {
status = "okay";
pinctrl-0 = <&i2c2m1_xfer>;
/* split mode: lane0/1 */
gc2053: gc2053@37 {
status = "okay";
compatible = "galaxycore,gc2053";
reg = <0x37>;
clocks = <&cru CLK_CAM0_OUT>;
clock-names = "xvclk";
/* Set pinctl of xvclk in &pinctl */
power-domains = <&power RK3568_PD_VI>;
reset-gpios = <&gpio4 RK_PB1 GPIO_ACTIVE_LOW>;
pwdn-gpios = <&gpio3 RK_PD0 GPIO_ACTIVE_LOW>;
/*power-gpios = <&gpio0 RK_PC1 GPIO_ACTIVE_HIGH>;*/
rockchip,camera-module-index = <0>;
rockchip,camera-module-facing = "front";
rockchip,camera-module-name = "rgbd";
rockchip,camera-module-lens-name = "Optics";
port {
gc2053_out: endpoint {
remote-endpoint = <&dphy1_in>;
data-lanes = <1 2>;
};
};
};
};
5. 异步注册核心函数调用流程
6. 所有设备注册顺序
v4l2-dev.c:
● __init videodev_init(void) 初始化函数申请了v4l2的字符设备号,但是并没有注册和关联具体驱动。
phy-rockchip-csi-dphy.c:
● rockchip_csi2_dphy_probe(struct platform_device *pdev) 异步注册csi2-dphy1子设备, 调用流程如下:
rockchip/isp/dev.c:
● int rkisp_plat_probe(struct platform_device *pdev) 注册rkisp-vir0父设备、isp-dubdev子设备、csi2-dev子设备等,由于rk3568支持多路sensor输入,即isp支持多路处理,因此会虚拟多通道isp-virx。调用流程如下:
i2c/gc2053.c
● int gc2053_probe(struct i2c_client *client, const struct i2c_device_id *id) 异步注册sensor子设备,调用流程如下: