王宝珠,程 杰
(河北工业大学 信息与工程学院,天津 300401)
由于网络与信息技术的不断发展,远程视频监控技术得到了广泛的推广,同时对视频传输的效率、功耗、实时性、分辨率以及传输设备的体积大小等方面提出了更高的要求。自从H.264编码标准发布以来,因其具有优异的压缩性能、很好的网络亲和性,获得了极大地支持与应用。但在很多应用场合是通过调用H.264编码库,实现了软件方式的编解码。本文采用拥有强大的多媒体处理能力ARM11芯片进行开发,它内部集成了专门处理多媒体数据的位处理器,通过ARM内部的MFC模块完成了对H.264的硬件方式的编解码。本论文视频服务器建立在具有丰富的网络协议、较强的稳定性的Linux系统上,完成了视频数据的采集、压缩,然后发送到Boa中,然后通过以太网发送到上位机进行显示,实现了远程的实时监控[1]。
本系统主要以友善之臂Tiny6410开发板作为视频服务器平台。Tiny6410核心板采用ARM1176JZF-S核设计的CPU,S3C6410内部集成了强大的多媒体处理单元,支持Mpeg4、H.264等格式的硬件编解码,核心板集成了256M的DDRRAM、1GB Nand Flash存储器,通过丰富的接口资源与外围电路相连接。本论文所涉及的主要接口包括标准DB9串口、SD卡接口、JTAG接口、USB串口以及网络接口。整个硬件系统框图如图1所示。
图1 硬件系统结构图Fig.1 Structure diagram of hardware system
在该硬件系统中现代的v500摄像头通过usb接口与开发板相连,向S3C6410提供YUY2格式的视频帧。目标板通过串口与宿主机连接,通过超级终端与目标板进行通信,对目标板进行控制和文件的传输。JTAG接口连接Jlink仿真器,通过宿主机上的rvds软件进行程序的调试。SD卡用于烧写superboot,然后完成整个linux系统的移植工作与应用软件的复制工作。服务器通过DM900网卡与远程客户端进行通信。
整个软件系统包括引导装入程序、Linux内核、文件系统、各种驱动程序以及应用软件组成。图2为视频服务器的软件结构框图。
图2 软件系统结构图Fig.2 Structure diagram of software system
在进行系统移植之前,首先在宿主机上建立开发环境,安装linux虚拟操作系统,安装编译调试软件RVDS,建立与目标板通信的超级终端,建立交叉编译环境等相关操作。
本系统首先在SD卡中烧写superboot,然后将Uboot引导程序移植到Nand Flash中,然后移植版本为Linux 2.6.38的内核,接着移植根文件系统Rootfs,这样整个操作系统环境就搭建完成了。在编译Linux内核之前,要配置本系统所需的驱动模块,将MFC驱动和万能摄像头驱动集成到内核中[2]。
V4L2是集成在Linux系统中的一个虚拟的设备驱动。主要功能是使应用程序发现多媒体设备,然后对设备进行操作管理。它提供了各种API接口,在本系统中完成了对摄像头视频流的捕获与输出,如图3为数据帧采集流程图[3]。
图3 数据采集流程Fig.3 Flow diagram of data capture
1)打开设备文件。 fd=open(Devicename,mode);第一个参数是注册在/dev/目录下的设备名,打开模式可分为阻塞和非阻塞模式。
2)获取设备属性。通过调用 ioctl(fd,VIDIO_QUERYCAP,&cp)获取打开设备相关参数存放到cp结构中。
3)设置捕获格式。 调用 ioctl(fd,VIDIOCS_FMT,&fmt)设置捕获图像的存储格式、宽带、高度、像素大小等。
4)为视频帧分配内存。 通过 ioctl(fd,VIDIOC_REQBUFS,&req)向内核申请req.count个缓存。
5)映射缓存。首先通过VIDIOC_QUERBUF获取缓存地址,然后mmap到用户空间。
6)视频帧的采集。调用read()将数据存放到缓存中。
7)处理采集数据。V4L2的数据缓存采用FIFO的方式,当应用程序将最先采到的一帧数据取走时,将重新采集最新的数据。
8)关闭视频设备。调用close()实现设备的关闭。
本系统通过S3C6410内部多媒体编解码模块实现H.264标准的视频压缩。采用硬压缩不占用CPU资源而且速度更快,为视频的实时传输做好了准备[4]。如图4为MFC编码流程图。
图4 h.264编码流程图Fig.4 Flow diagram of h.264 encoder
1)初始化H.264编码环境。调用SsbSipH264 EncodeInit(Width, Height, Framerate, Bitrate, GOPNum) 来打开 MFC设备并且对编码结构参数进行初始化。
2)设置编码参数。调用SsbSip H264 EncodeS et Config(open Handle,type,value)对编码的各种参数进行配置。
3)获得视频输入地址。通过SsbSipH264EncodeGetInBuf(openHandle,size)获取视频输入地址。
4)通过 memcpy(p_inbuf, in_addr, frame_size)将需要编码视频帧复制到编码时存放原始数据的缓存中。
5)通过 SsbSipH264EncodeExe(handle)函数进行编码压缩。
6)关闭设备,调用 SsbSipH264 EncodeDeInit(handle)函数释放占用资源并且关闭设备。
本系统将boa移植到运行在ARMM11开发板上的Linux系统中,建立了嵌入式web服务器,为远程客户端提供基于HTTP协议的网络接入方式。Boa支持基于CGI的动态网页,因此采用编写CGI脚本对远程客户端的请求进行响应,发送经过编码的视频数据包。如图5为boa中视频传输的流程图[5]。
图5 数据传输流程图Fig.5 Flow diagram of data transmission
1)完成boa服务器的初始化工作。
2)通过socket创建流式套接字,并获得套接字描述符。
3)通过bind将套接字与服务器地址绑定。
4)通过listen对端口进行监听。
5)通过accept等待来自客户端的连接请求。
6)建立相互的连接,分析客户端命令。
7)执行CGI脚本程序,发送数据。
8)关闭套接字,结束通信。
工作在pc机上的远程客户端从网络接收视频数据包,然后对视频帧进行解码与在屏幕上显示图像。本系统采用基于开源的SDL与FFmpeg库提供的API接口,实现对视频的解码与播放[6]。
1)首先进行初始化操作。avcodec_register_all();avdevice_register_all();av_register_all();通过以上函数注册所有的编解码器,复用分离器,文件格式的注册。
2)设置 AVFormatContext结构体,对整个编码过程所需要的各种参数进行设置。
3)从以上结构体中找到相关解码器的上下文。
4)调用avcodec_open()函数打开 H.264解码器。
5)调用avcodec_alloc_frame()函数分配内存来存储解码后得到的yuv数据。
6)通过 avcodec_decode_video(p Codec Ctx, Inbuf, &count,outbuf, sizeof(outbuf))函数对数据进行解码,pCodecCtx 是解码器的上下文,Inbuf指向解码后数据的位置,count是已完成的帧数,outbuf指向被解码解码的原始数据。最后调用SDL库中的函数来实现视频的显示。
本文完成了远程视频监控包括数据采集、数据压缩、数据传输、数据显示的整个模块设计。采用了性价比很高的ARM11作为整个服务器的数据处理核心,搭载了开源的具有很好的网络亲和性和稳定性的Linux操作系统,使得应用软件有一个高效和稳定的运行环境。实现了对视频数据的H.264标准的硬压缩,极大提高了数据的处理与传输效率,使得整个系统具有较好好的实时性。在该系统的基础上,可以进行功能的增加和优化,实际应用于各种监控场合。
[1]叶俊华.ARM11的嵌入式视频处理终端设计[D].长沙:中南大学,2009.
[2]杨牟刚.基于嵌入式Linux的网络视频监控系统设计与实现[D].桂林:桂林电子科技大学,2008.
[3]张建江.基于嵌入式Linux的H.264视频接收系统设计[D].西安:西安电子科技大学,2008.
[4]罗智勇.针对视频会议应用的H264视频编码器研究与实现[D].广州:暨南大学,2005.
[5]黄恒强.基于ARM和Linux的嵌入式远程视频监控系统设计[D].南京:南京理工大学,2008.
[6]胡杰.基于ARM的嵌入式视频监控终端的研究[D].武汉:武汉理工大学,2008.