前几天在 rvspoc 看到一个 V4L2 驱动开发的比赛题目,可以看看上面有没有什么pr,然后以此来进行进一步的学习,发现还真有一个pr,遂学习,作为一个新手,上面的内容无论是从简单的输出还是从设备的注册来说,都有很多值得学习的地方,感谢开发者的贡献。
参考资料:
调试信息分级?
原代码中,调试信息分级是通过这种方法来进行的,也就是 define 输出宏,然后再在里面判断调试等级并决定是否输出某些内容,输出顺序从 ERR > WARNING > INFO > DEBUG
内核模块,从哪里入手呢
首先找到
module_init
,设置了 sg2000_video_init
。在这个方法内又调用了两个方法: platform_device_register
和 platform_driver_register
。这两个方法都是在 #include <linux/platform_device.h>
被引入的。头文件并没有给出很多的信息,但我们大概知道了调用的方法,就把它当作抽象的方法来看吧。这两个方法分别又传入了两个结构体,内容分别为
对应三个方法:
sg2000_video_device_release
、 sg2000x_video_probe
和 sg2000x_video_remove
在这里,
sg2000_video_device_release
和 sg2000x_video_remove
一个是空的,一个就是对设备的反注册,所以我们着重看 sg2000x_video_probe
,这也是视频设备的初始化函数。从初始化函数 sg2000x_video_probe
入手!
这个函数总体来说可以分为几步:
- 注册 V4L2 设备
- 初始化 vb2 队列,在队列中告知功能类型、IO模式、缓冲区结构体大小
- 使用
video_set_drvdata
存入 video_device ,这样后面就能通过 *file 指针 +video_drvdata
方法重新拿回这个私有数据结构的指针,因为你向 v4l2 注册只能注册 vdev ,所以还要在 vdev 里面存入这个私有数据结构的指针
- 使用
video_register_device
注册 /dev/videoX
引入了两个新概念,v4l2 和 vb2 ,以及一个私有数据结构。
v4l2 是干什么的呢?v4l2 就是用来创建一个像 /dev/videoX 这样的设备文件的,使得无论是什么品牌、接口,都可以通过这个标准文件进行访问。而 vb2 是视频缓冲区管理库,用来干实际的脏活,把数据从硬件(?)上搬到缓冲区上,然后再端给 v4l2 。
同时还有一个 video_device 的模板