甘勤操,陈西曲
(武汉轻工大学电气与电子工程学院,湖北武汉430023)
远程监控是指本地的PC机通过网络系统对远端的情况进行实时的视频监控,通过远程监控,工作人员可以足不出户就了解现场的情形,及时的对突发事件进行处理。但传统的远程监控存在很多不足之处:①普遍采用的同轴电缆进行传输,传输距离近,传输质量差;②无法在室外实时掌握监控的情况[1]。随着计算机技术,通讯技术,网络技术的快速发展和迅速普及,促进了基于互联网技术的产生以及发展,传统的模拟视频监控系统和基于PC机的数字视频监控系统已不能满足社会发展的需求,基于互联网技术的远程监控系统不受地域限制进行监控,基于嵌入式的网络监控系统逐渐得到了关注,在越来越多的领域得到了应用,它具有功能强,实时性强,可靠性高和结构小巧等优点。本设计基于ARM平台及linux操作系统进行设计,具有可移植性高,组网能力强,视频传输能力强等特点,在PC机上进行监控,在传统监控的基础上,在开发板上外接一个LCD,可以在室外看到监控影像。
硬件平台是整个系统的基础,起到至关重要的作用。为了满足视频采集,压缩,传输带来的巨大运算量,必须有一款功能强大的处理器器,本系统采用的处理器是三星公司出产的S3C2440处理器,这款处理器基于ARM9构架开发,运行主频为400 MHz,最高主频可达533 MHz,芯片上集成有Camera解码器,可以完成摄像头数据的解码,无需再安装解码器。开发板与PC机之间的数据交互依靠串口来实现。开发板外接一个3.5吋的LCD显示器用于显示视频数据。视频采集用的是普通的USB摄像头,视频传输采用的是DM9000网卡,视频信号通过网卡进行传输[2]。嵌入式视频监控系统硬件结构如图1所示。
图1 硬件结构图
整个系统的工作原理是:系统通过V4L2提供的统一的API提取摄像头原始数据,数据格式为YUV 4:2:2这些数据转换成RGB24数据,然后开辟两个线程,一个线程将数据写入开发板的LCD缓冲区,就可以直接预览显示视频,另一个线程将数据通过TCP/IP发送到远端PC机。
视频传输模块是本设计的重要模块,S3C2440采用的DM9000网卡,它有一个一般处理接口,一个10/100 M自适应的PHY和一个4 kB的DWORD值的SRAM。DM9000采用100引脚的TQFP封装,是小型化及对成本敏感的以太网应用的理想选择。图2是DM9000在开发板上的连接。
图2 DM9000网卡连接图
鉴于Linux开源,稳定且具有良好的移植性和优秀的网络功能,采用Linux操作系统作为软件开发平台。首先将在PC机上编译好的内核和文件系统移植到开发板上,系统主要由视频采集模块,数据处理模块,图像显示模块组成,其中视频采集模块由USB摄像头,USB驱动程序两部分组成。数据处理模块由V4L2采集程序组成,图像显示模块由运行于PC机上的解码显示程序以及开发板上外接的LCD显示器担当,可以在两地同时显示影像。传输层有两种协议可供选择,一种是TCP协议,一种是UDP协议,因为TCP协议用一个校验和函数来检验数据是否有错误;在发送和接收时都要计算和校验,如果出错要进行数据重新传输,传输的质量高,所以传输协议选用TCP协议[3]。
Video for Linux two简称 V4L2,是基于 V4L的不足而优化的版本。V4L2提供了统一的API接口,用于在linux操作系统下进行视频采集。在视频监控系统和嵌入式多媒体终端中都有广泛的应用。
在Linux下,所有外设都被看成一种特殊的文件,成为“设备文件”,可以像访问普通文件一样对其进行读写。一般来说,采用V4L2驱动的摄像头设备文件是/dev/video0。为了通用,可以建立一个到/dev/video0的链接。V4L2支持两种方式来采集图像:内存映射方式(mmap)和直接读取方式(read)。本文采用的是mmap模式。具体视频采集流程如图3所示。
V4L2视频采集主要步骤如下:
1)打开视频设备,得到文件描述符在Linux下,摄像头硬件已经被映射为设备文件“/dev/video%d”,用linux下的库函数open()打开这个设备文件,获得其文件描述符fd_v4l2,然后对这个文件描述符进行参数初始化。
2)打开视频设备后,可以设置该设备的属性,例如裁剪等,这一步是可选的。
3)设置摄像头的制式为PAL,获取并记录缓冲的物理空间。
图3 视频采集流程
4)将申请到的缓冲区放入视频采集队列,用来存放采集到的数据。
5)设置视频的采集方式为内存映射方式。
6)处理采集数据。为实现连续的视频帧数据采集,需要用帧缓冲区队列来实现。启动视频采集后,内核驱动开始采集数据,采集到的数据被放入输入队列的第一个帧缓冲区,一帧数据采集完成后,内核驱动将填满数据的这一帧缓冲区移至视频采集输出队列,等待应用程序从输出队列取出。内核驱动接下来采集下一帧数据,放入第二个帧缓冲区,帧缓冲区存下一帧数据后,被放入视频采集输出队列。应用程序从视频采集输出队列中取出含有视频数据的帧缓冲区,取出帧缓冲区中的视频数据,然后开辟两个线程,一个线程通过TCP/IP协议将视频数据发送到PC端,一个线程将视频数据传递给LCD显示模块。最后,应用程序将处理完数据的帧缓冲区重新放入视频采集输入队列,用于填充新的数据,这样可以循环采集,输入输出队列如图4所示。
7)关闭视频设备,首先用VIDIOC_STREAMOFF命令标示符停止视频采集,再用close(fd)关闭标示符。
图4 视频采集输入输出队列
V4L2从摄像头采集到的数据格式是YUV4:2:2类型的,要将其解码成RGB24以便传输显示。将YUV4:2:2 的 4byte(Y0,U0,Y1,V1)数据转换为RGB24 的 6byte(R1,G1,B1,R2,G2,B2)[4]数据。
驱动程序采集的原始数据格式为YUV4:2:2,存放的码流为:Y0 U0 Y1 V1 Y2 U2 Y3 V3,映射出像素点为:[Y0 U0 V1][Y1 U0 V1][Y2 U2 V3][Y3 U2 V3],每一个YUYV占4个字节内存,用来映射两个像素点。将 (Y0U0V1)转换为(R1G1B1),将(Y1U0V1)转换为(R2G2B2)。
转换核心代码如下:
R1=(298*Y0+409*V1+128)>>8;
G1=(298* Y0-100*U0-208*V1+128)>>8;
B1=(298*Y0+516*U0+128)>>8;
R2=(298*Y1+409*V1+128)>>8;
G2=(298*Y1-100*U0-208* V1+128)>>8;
B2=(298*Y1+516*U0+128)>>8;
这样就将一个YUV4:2:2数据转化为两个RGB24数据。经过编码的数据可以直接在LCD屏上显示。
本设计采用的是TCP/IP协议的socket来进行视频数据的传输,首先调用socket()函数建立一个套接字,然后调用bind()函数绑定本地IP地址以及端口号,接着调用listen()函数监听监控主机发来的连接请求,TCP连接要进行3次握手,然后调用send()函数将数据发送到监控主机。视频发送流程如图5所示。
本系统中视频会在LCD和PC下同时显示,本文主要介绍在LCD下的显示。
在linux下定义了 FrameBuffer设备,Frame-Buffer设备提供了一个图形硬件抽象层,代表视频硬件的帧缓冲。
图5 视频发送流程
在应用程序中,一般通过将FrameBuffer设备映射到进程地址空间的方式使用,在本系统中LCD被映射为/dev/fb0,首先打开/dev/fb0设备,并通过mmap系统调用进行地址映射,然后将视频数据按顺序依次写入缓冲区,这样数据就可以直接显示在LCD上了。
开发板上电,系统加载应用程序,在PC机上打开M-JPEG viewer客户端,输入系统正确的IP地址(监控服务器的本地IP地址)及端口号(监控服务器的通信端口号),点击客户端上的connect按钮,利用wireshark网络抓包程序可以捕捉到PC机与监控开发板建立网络连接的过程。分析图例,可以判断网络部分工作正常,其中192.168.1.101 为PC 机IP 地址192.168.1.103为开发版IP地址。如图6所示。
图6 TCP三次握手
当网络连接建立后,开始传输视频数据,图7为wireshark捕捉到的网络发送的数据。
图7 网络传输的视频流
客户端接受开发板放送来的数据,将每一帧图片显示在PC机屏幕上。图8是客户端解码后显示的视频截图。
开发板可以将视频数据直接显示在开发板外接的LCD上,可以在室外观察监控的效果,实时性和灵活性更强。图9为开发板LCD视频截图。
图8 监控主机视频截图
图9 开发板上视频截图
客户端可以同时在多台主机上面运行,多名工作人员可以在不同的地方同时进行监控,增加了系统的灵活性。
本文介绍了一种基于ARM9来完成视频监控的设计方法,详细介绍了视频采集模块在linux下的实现过程。视频信号的采集是视频监控终端设计的重要环节,本设计在ARM平台上完成各项试验测试,视频采集信号流畅,实时性强,而且采用的是模块化设计,系统升级时只需升级相应模块就可以。实验证明,在嵌入式操作平台上以软件的方式实现视频监控具有可操作性强的特点,系统应用范围广,前景广阔。
[1]潘国辉.安防天下——智能网络视频监控技术详解与实践[M].北京:清华大学出版社,2010:21-23.
[2]韦东山.嵌入式 Linux应用开发完全手册[M].北京:人民邮电出版社,2011:86-87.
[3]理查德·史蒂文斯.TCP/IP详解(卷一)[M].陆雪莹,译.北京:机械工业出版社,2000:147-149.
[4]刘峰.视频编码技术与国际标准[M].北京:北京邮电出版社,2005:133.