版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
学士论文基于Cortex-A8的视频监控系统的设计.3OV9650摄像头驱动程序开发此次用的摄像头正是挂载在I²C上的,所以需要将摄像头芯片配置数据的写入是通过I²C总线。(1)Camera控制器的总体示意图如下:图4.SEQ图4.\*ARABIC4Camera控制器整体框图(2)S5PC100芯片上所集成的CAMIF模块引脚:图4.SEQ图4.\*ARABIC5S5PC100的camera控制器I/O引脚CAM_PCLK:PixelClock像素时钟CAM_VSYNC:FrameSync帧/场同步信号CAM_HREF:HorizontalSync行同步信号CAM_D[7:0]:PixelData像素数据CAM_MCLK:系统时钟信号CAM_RST:SoftwareResetorPowerDown复位信号CAM_FILELD:FIELDsignal像素填充信号下面我们来看看摄像头控制器的工作时序:图4.SEQ图4.\*ARABIC6CAMI/F时序图和数据我们使用的摄像头型号是ov9650,130万像素,是采用cmos接口的图像传感器芯片,可以感知外部的视觉信号并将其转换为数字信号并输出。控制部分为摄像头上电、IIC控制接口,数据输出为摄像头拍摄的图传到主控芯片,所有要有data、行场同步和时钟号。GT2021/GT2021是CMOS接口的图像传感器芯片,可以感知外部的视觉信号并将其转换为数字信号并输出。我们需要通过MCLK给摄像头提供时钟,RESET是复位线,PWDN在摄像头工作时应该始终为低。PCLK是像素时钟,HREF是行参考信号,VSYNC是场同步信号。一旦给摄像头提供了时钟,并且复位摄像头,摄像头就开始工作了,通过HREF,VSYNC和PCLK同步传输数字图像信号。数据是通过D0~D7这八根数据线并行送出的。ov9650向外传输的图像格式是YUV的格式,我们使用的是YCbCr(8bits,4:2:2)。
(4)摄像头驱动文件简要分析:
ov9650内部有上百个寄存器需要配置,我们的摄像头是挂接在I²C总线上的一个设备,因此通过I²C去配置这些寄存器。驱动代码采用的总线驱动代码是由samsung公司提供的I²C-s3c2410.c,提供I²C适配器与从设备间完成数据通信的能力,比如起始,停止,应答信号和master_xfer的实现函数。
ov9650.c是一个客户驱动是对从设备的一种操作实现ov9650_init: 在I²C总线上挂接设备调用I²C_add_driver(&ov9650_driver),他最终会调用到的是ov9650_probe函数。ov9650_probe: 主要是对ov9650从设备的初始化工作,其中最开始是判断ID是否相匹配,匹配后通过核心层的intI²C_transfer(structI²C_adapter*adap,structI²C_msg*msgs,intnum)配置cmos内部各个寄存器,比如数据格式配置为YUYV422格式,输出大小为640*480的VGA模式。
s5pc100_camera.c文件中的FIMC控制器驱动:该驱动最终生成V4L2标准设备/dev/videoX,向上提供ioctl,mmap等函数接口,在应用程序中我们可以通过这些接口去控制摄像头工作。
s5pc100_camera_init();
platform_driver_register(&s5pc100_camera_driver);//注册平台驱动可以看出是以平台机制来编写的。s5pc100_camera_probe(structplatform_device*cam);probe函数遵循平台机制的基本写法:配置功能管脚,构建设备结构体,获取平台资源,映射资源,设置结构体,保存结构体,配置寄存器,向上注册V4L2设备。我们通过linux驱动知识和芯片手册相关参数可完成camera驱动编写,接下来就是camera驱动移植过程:(1)修改uboot的drivers/I²C/busses/Kconfig configI²C_S3C2410 tristate"S3C2410I²CDriver"dependsonARCH_S3C2410||ARCH_S3C64XX||ARCH_S5PC100(2)内核配置I²C设备支持并重新编译内核(3)修改viarch/arm/mach-s5pc100/mach-smdkc100.c查看原理图可以知道我们的摄像头是接在I²C-1上所以修改I²C_devs1添加ov9650的内容,主要是ov9650的地址,这个在芯片手册上可以查到是0x30。修改:staticstructI²C_board_infoI²C_devs1[]__initdata={};为:staticstructI²C_board_infoI²C_devs1[]__initdata={ {I²C_BOARD_INFO("ov9650",0x30),},};添加s5pc100摄像头控制器平台设备相关内容,这些内容我们可以通过查看S5PC100的芯片手册查到staticstructresources3c_camif_resource[]={ [0]={.start=0xEE202100, .end=0xEE202100+SZ_1M-1, .flags=IORESOURCE_MEM,}, [1]={.start=IRQ_FIMC0, .end=IRQ_FIMC0, .flags=IORESOURCE_IRQ,}};staticu64s3c_device_camif_dmamask=0xffffffffUL;structplatform_devices3c_device_camif={ .name ="s5pc100-camif", .id =0, .num_resources=ARRAY_SIZE(s3c_camif_resource), .resource =s3c_camif_resource, .dev={ .dma_mask=&s3c_device_camif_dmamask, .coherent_dma_mask=0xffffffffUL }};EXPORT_SYMBOL(s3c_device_camif);注册摄像头控制平台设备:在smdkc100_devices中添加s3c_device_camifstaticstructplatform_device*smdkc100_devices[]__initdata={ &s3c_device_camif,//添加内容};(4)使用makemenuconfig图形界面,添加V4L2驱动支持即可成功驱动摄像头了。5.视频数据处理和传输模块5.1基于Video4Linux2的视频采集模块开发摄像头驱动程序安装好后为了进行视频采集必须加入Video4Linux2模块,从而可以通过Video4Linux2模块提供的编程接口(API)从摄像头设备中获取图像帧。Video4Linux2是VideoForLinuxTwo的简称[18],是Linux系统下进行视频音频等应用开发的应用编程接口,同时也提供了无线电通信和文字电视广播解码等的数据接口,结合视频采集设备和相应的驱动程序,可以实现音影图像采集、AM/FM广播等功能,在远程会议、可视、视频监控系统中有着广泛的应用本文所述正是基于Linux系统下,进行视频图像采集、显示播放的应用程序开发,在此程序基础上可以进行图像识别视觉导航等高级应用的二次开发。5.1.1摄像头驱动加载在Linux下,所有的外设均被看成是一种特殊文件进行处理,称之为设备文件。系统调用及各种函数库直接或间接地提供了内核和应用程序之间的接口,而设备驱动程序则是内核和外设之间的接口,它完成设备的初始化和释放、对设备文件的各种操作和中断处理等功能。由于屏蔽了外设硬件的细节,使得应用程序可以像普通文件一样对外设进行操作而无需关注其具体的细节因此,在进行图像采集程序设计之前,必须先加载CMOS摄像头的驱动模块。staticint__inits5pc100_camera_init(void){platform_driver_register(&s5pc100_camera_driver);return0;}5.1.2Video4Linux2程序设计下面通过使用VideoLinux2应用编程接口提供的有关数据结构定义和函数库,编写视频视频图像采集程序。程序流程如图所示:图5.SEQ图5.\*ARABIC1视频图像采集程序流程图1)打开视频设备文件intfd=open(“/dev/video0”,O_RDWR);if(fd<0){printf(“Openfailed!\n”;exit)}打开视频设备后,我们可以获取相应的文件描述符,在后面程序中通过使用此文件描述符对设备进行操作;若打开失败,则返回相应的错误信息。2)获取视频设备相关属性Structv4l2_capabilitycap;if(-1==ioctl(fd,VIDIOC_QUERYCAP,&cap)){printf(“can’tgetcap!\n”);exit(-1);if(cap.capabilities&V4L2_CAP_VIDEO_CAPTURE)printf(“itisacapturedevice!\n”);if(cap.capabilities&V4L2_CAP_STREAMING)printf(“itsupportstreamingi/0\n”);}在Linux程序设计中ioctl调用有点像是大杂烩,它提供了一个用于控制设备及其描述符行为和配置底层服务的接口,对设备的I/O通道进行管理。终端、文件描述符、套接字甚至磁带机都可以使用为它们定义的ioctl,在V4L2中也是通过ioctl函数对设备进行编程的其原型为:intioctl(intfildes,intcmd,...);ioctl对描述符fildes指定的对象执行cmd参数中给出的操作,根据具体函数还可能有一个可选的第三参数如上所示,调用VIDIOC_QUERYCAP来取得设备文件的属性参数并存储于cap结构中,然后利用与操作可以分别检验并显示出设备的相关属性。3)设置图像采集格式structv4l2_formatfmt;fmt.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;fmt.fmt.pix.width=640;fmt.fmt.pix.height=480;fmt.fmt.pix.pixelformat=V4L2_PIX_FMT_YUYV;if(-1==ioctl(fd,VIDIOC_S_FMT,&fmt)){printf("FMTfailed\n");exit(-1);}将fmt结构填入适当的值,然后通过传递VIDIOC_S_FMT命令参数对设备的图像采集格式进行初始化,如上所示,将视频图像采集格式设为YUYV格式,大小设为640*480。4)内存映射初始化在Video4Linux2下截取图像有两种方式:mmap内存映射方式和直接读取设备方式。在属性检验中可知此设备不支持读写操作,而且前者采用共享内存通信,不需要任何数据的拷贝,效率高,因此我们选用mmap内存映射方式,这也是程序设计中的一个难点。(1)定义内存映射模式以及缓存数量调用带VIDICO_REQBUFS命令参数的ioctl函数分配自定义的缓存数量,这在初始化中是必须的一步。structv4l2_requestbuffersreqbuf;reqbuf.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;reqbuf.count=30;reqbuf.memory=V4L2_MEMORY_MMAP;if(-1==ioctl(fd,VIDIOC_REQBUFS,&reqbuf)){printf("RE-QBUFSfailed\n");exit(-1);}(2)在设备驱动和应用程序间内存映射guchar*buffers=calloc(reqbuf.count,sizeof(*buffers));//分配用户内存for(inti=0;i<reqbuf.count;i++){structv4l2_bufferbuffer;buffer.type=reqbuf.type;buffer.memory=V4L2_MEMORY_MMAP;buffer.index=i;if(ioctl(fd,VIDIOC_QUERYBUF,&buffer)==-1){printf("QUERYBUFfailed\n");exit(-1);}buffers[i].start=mmap(NULL,buffer.length,PROT_READ|PROT_WRITE,MAP_SHARED,fd,bufer.m.offset);}首先是分配用户内存,然后利用for循环中分别对各个缓存进行映射,其偏移量和缓存大小在VIDIOC_QUERYBUF命令参数的ioctl函数中定义,最后用mmap()函数将在设备缓存和应用程序所分配内存间建立映射,并返回应用程序内存的首地址,至此内存映射初始化完毕。(3)将缓存加入等待输入缓存队列,准备采集图像数据调用VIDIOC_QBUF命令参数的ioctl函数在for循环中将空缓存加入等待输入缓存队列,在缓存加入等待输入队列后,调用一次VIDIOC_STREAMON命令参数的ioctl函数,此时就可以使用这些缓存进行图像数据了。for(inti=0;i<reqbuf.count;i++){structv4l2_bufferbuf;buf.type=V4L2_BUF_TYPE_VIDEO_CAPTURE;buf.memory=V4L2_MEMORY_MMAP;buf.index=i;if(-1==(ioctl(fd,VIDIOC_QBUF,&buf))printf("QBUFfailed\n");}type=V4L2_BUF_TYPE_VIDEO_CAPTURE;if(-1==ioctl(fd,VIDIOC_STREAMON,&type))printf("STREA-MONfailed\n");采集到的数据由此交给视频流服务器来处理。5.2视频流服务器分析及图片裁剪本次课题我们采用的是开源软件mjpg-streamer视频流服务器。A8主服务器通过摄像头捕获图像存入staticglobalsglobal中的buf中,然后通过各个输出模块进行处理。图5.SEQ图5.\*ARABIC2视频流服务器总体框架图input_uvc.so:输入组件,主要负责初始化全局结构体、操作摄像头、处理和保存图像数据。output_file.so:输出组件,主要负责保存jpeg图像到本地。以线程方式运行,循环的间隔指定时间将图片保存到本地。通过简单地open(),wirte()读写操作将保存图片到指定的路径,文件名随时间变化。output_http.so:输出组件,通过网络socket将图片传送到网络是用户可以在远端查看视频、图片等。图像以stream流的形式发送可确保数据完整。每次发送一帧图像都要先发送一个MJPEG协议头每次发送完一帧图像数据后都要发送一个边界字符串表示数据发送完成。循环发送通过一帧帧显示形成视频。该组件中server_pthread函数使用多线程的方式实现的并发服务器,也就是为每一个连接请求的客户端创建一个client_thread线程,该线程独立和服务端通信,发送图像数据。output_lcd.so:我们自己增加的输出组件,视频流服务器使用的是v4l2的接口,经过修改可以各使得各输出模块能够通过共享内存获取图像数据,可以保存到文件,可以以HTTP方式访问UVC兼容摄像头新增output_lcd可以直接copy到LCD的显存。我们将修改后的视频流服务器移植到我们的主程序中,实现了视频数据处理。并且output_lcd部分我实现了图片裁剪,图片有640*480裁剪至480*272,以适应我们本次试验使用的LCD。图片裁剪过程如下图:图5.SEQ图5.\*ARABIC3图片格式转换及裁剪过程所修改实现采集(640*480->480*272)关键代码:intbmp2fb16_rgb565(unsignedchar*bmpdata,unsignedshort*fb16){intx,y;unsignedshortr,g,b;unsignedshortpixel16;unsignedshort*fb16_buff;fb16_buff=fb16;for(y=0;y<480;y++){/*copyonelinetoframebuffer(Y轴方向只转换104-376共272个像素)*/if(y<104){bmpdata+=3*640;continue;} if(y>376)break;for(x=0;x<640;x++){ /*copyonepixeltoframebuffer(X轴方向只转换100-579共480个像素)*/if(x<100||x>579){bmpdata+=3;continue;}b=*bmpdata;bmpdata++;b>>=3;g=*bmpdata;bmpdata++;g>>=2;r=*bmpdata;bmpdata++;r>>=3;pixel16=(unsignedshort)((r<<11)|(g<<5)|b); *(fb16_buff+((y-104)*LCD_X+(x-100)))=pixel16;}}return0;}5.3LCD驱动开发和移植本课题实验所使用的TFT-LCD在linux内核中属于帧缓冲设备,帧缓冲(Framebuffer)是Linux为显示设备提供的一个接口,它允许上层应用程序在图形模式下直接对显示缓冲区进行读写操作。5.3.1LCD参数分析图5.SEQ图5.\*ARABIC4CPU上与LCD相关的PIN引脚图5.SEQ图5.\*ARABIC5LCD控制器时序图TFT屏是目前嵌入式系统应用的主流,上图所示给出了TFT屏的典型时序。时序图中的VCLK、HSYNC和VSYNC分别为像素时钟信号(用于锁存图像数据的像素时钟)、行同步信号和帧同步信号,VDEN为数据有效标志信号,VD为图像的数据信号。作为帧同步信号的VSYNC,每发出一个脉冲,都意味着新的一屏图像数据开始发送。而作为行同步信号的HSYNC,每发出一个脉冲都表明新的一行图像资料开始发送。在帧同步以及行同步的头尾都必须留有回扫时间。这样的时序安排起源于CRT显示器电子枪偏转所需要的时间,但后来成为实际上的工业标准,因此TFT屏也包含了回扫时间。下图给出了LCD控制器中应该设置的TFT屏的参数,其中的上边界和下边界即为帧切换的回扫时间,左边界和右边界即为行切换的回扫时间,水平同步和垂直同步分别是行和帧同步本身需要的时间。xres和yres则分别是屏幕的水平和垂直分辨率。图5.SEQ图5.\*ARABIC6LCD控制器中的时序参数设置本课题实验所使用的LCD:夏普LQ043T3DX02、4.3英寸、分辨率为480*272(即一帧包含的像素点,水平方向480个像素,垂直方向272个像素)。显示模式(位数):可支持到32bpp,兼容24bpp、16bpp。图5.SEQ图5.\*ARABIC7夏普LCD硬件参数根据S5PC100芯片手册和图5-6中的LCD参数手册我们可以得出LCD控制寄存器应填入的值,从而得出lcd的平台资源,我们就能完成对LCD驱动的编写。5.3.2LCD驱动开发要在Linux平台上开发LCD驱动,那首先必须了解linux内核中的帧缓冲子系统。帧缓冲子系统包括以下几个文件:Fbmem.c(核心层、提供通用接口)、S3c-fb.c(控制器驱动层、配置相关寄存器)、Dev-fb.c(资源层、提供寄存器的地址)。在这里我们对这些文件做简要分析。核心层Fbmem.c:staticint__init
fbmem_init注册函数,所做的工作是创建虚拟文件、注册设备号、绑定操作方法接口、创建一类fb设备。staticconststructfile_operationsfb_fops实现接口open、read、write、ioctl、mmap等,以便应用程序调用。驱动层s3c-fb.c:驱动是采用平台设备机制编写的,在驱动注册函数中用platform_driver_register函数向平台设备虚拟总线注册。在结构体staticstructplatform_drivers3c_fb_driver中实现帧缓冲设备驱动的模块加载、卸载及平台驱动的探测和移除函数的模块。在函数staticints3c_fb_blank实现对LCD的相关控制。帧缓冲设备参数设置函数是staticints3c_fb_set_par(structfb_info*info),有些驱动支持多窗口显示,那么每个窗口匹配探测成功后都会执行到这个函数,这个函数中会设置LCD的工作时序,寄存器配置,显存地址,透明度等相关特效,窗口坐标等。资源层dev-fb.c:结构体staticstructresources3c_fb_resource[]中定义了帧缓冲设备相关的各种资源,有I/O资源,I/O中断资源等,另外有平台设备结构体structplatform_devices3c_device_fb,里面存放的是这个平台设备的相关属性。我们对这三个文件根据此次使用的LCD和linux内核版本做了对应修改之后,就可以添加到平台资源中完成开发。1)在文件mach-smdkc100.c里面修改lcd平台资源(根据芯片手册).win_mode={
.pixclock=/*像素时钟(皮秒)*/1000000000000ULL/((2+2+41+480)*(2+10+2+272)*80),
.left_margin=2,/*行切换:从同步到绘图之间的延迟*/
.right_margin=2,/*行切换:从绘图到同步之间的延迟*/
.upper_margin=2,/*帧切换:从同步到绘图之间的延迟*/
.lower_margin=2,/*帧切换:从绘图到同步之间的延迟*/
.hsync_len=41,/*水平同步的长度*/
.vsync_len=10,/*垂直同步的长度*/
.xres=480,/*宽度*/
.yres=272,/*高度*/
},.max_bpp=32,/*每像素最大位数,BPP*/.default_bpp=16,/*每像素默认位数,BPP*/}2)修改drivers/video/Kconfig修改:dependson(FB&&ARCH_S3C64XX)(移植驱动的时候很多地方都要修改这个图形界面的依赖,不然图形界面相应的选项出不来)为:dependson(FB&&ARCH_S3C64XX)||(FB&&ARCH_S5PC100)3)配置内核的图形界面配置内核添加对帧缓冲设备支持和LCD匹配。此时编译内核,LCD基本移植完成。我们在视频流服务器中的全局结构体中添加rgb_buf成员并分配空间,然后在compress_yuyv_to_jpeg转换函数中将RGB分量以rgb565的格式填充到rgb_buf。然后我新增了一个output_lcd.so组件,能够完成对LCD的初始化映射显存然后将全局的rgb_buf中间部分区域copy进显存就OK了。下面是我们采集的视频数据利用LCD在本地显示实现图:图5.SEQ图5.\*ARABIC8视频流LCD在服务器端本地显示5.4视频流网络发送的实现5.4.1socket网络编程Socket是一种网络接口,可以被看成是网络通信的一个端点。Socket接口在网络通信时使用Linux系统I/O的概念,也就是说,Socket接口模型仍采用“打开-读-写-关闭”的方式。Linux支持多种套接字,它既适用于一般的进程间通信,也适用于网络环境的进程通信。无连接时服务器也必须先启动,否则客户端请求传不到服务进程。无连接客户不调用connect()。因此在数据发送之前,客户端与服务器之间尚未建立完全相关,但各自通过socket()和bind()建立了半相关。发送数据时,发送方除指定本地套接字号外,还需指定接收方套接字号,从而在数据收发过程中动态地建立全相关。socket提供下列三种类型套接字[19]:(1)流式套接字(SOCK_STREAM):提供了一个面向连接、可靠的数据传输服务,数据无差错、无重复地发送,且按发送顺序接收。内设流量控制,避免数据流超限;数据被看作是字节流,无长度限制。(2)数据报式套接字(SOCK_DORAM):提供了一个无连接服务。数据包以独立包形式被发送,不提供无错保证,数据可能丢失或重复,并且接收顺序混乱。(3)原始式套接字(SOCK_RAW):该接口允许对较低层协议,如IP、ICMP直接访问。常用于检验新的协议实现或访问现有服务中配置的新设备。本系统中采用的是流式套接字,下面介绍socket编程中的主要函数[20]:创建套接字socket():该函数用于建立一个socket连接,可指定socket类型等信息。在建立了socket连接之后,可以对socketadd或sockaddrin进行初始化,保存所建立的信息。bind():该函数是用于将本地口地址绑定端口号的,主要用于TCP的连接。当一个套接字用socket()连接后,存在一个名字空间(地址族),但它没有被命名。bind()将套接字地址(包括本地主机地址和本地端口地址)与所创建的套接字号联系起来,即将名字赋予套接字,以指定本地半相关。connect()和accept():这两个系统调用用于完成一个完整相关的建立,其中connect()用于建立连接。无连接的套接字的进程,也可以调用connect(),但这时在进程之间没有实际的报文交换,调用将从本地操作系统直接返回。而accept()用于使服务器等待来自某客户进程的实际连接。listen():函数listen()仅被TCP服务器调用。它做两件事情,当函数socket()创建一个套接口时,被假设为一个主动套接E1。也就是说,它是一个将调用connect()发起连接的客户套接口,函数listen将未连接的套接口转换成被动套接口,指示内核应接受指向此套接口的连接请求。根据TCP状态转换调用函数listen()导致套接口从CLOSED状态转换到LISTEN状态。此调用用于面向连接服务器,表明它愿意接收连接。listen()需在accept()之前调用。send()和recv()这两个函数用于接收和发送数据,可以用于TCP中,也可以用于UDP中。当一个连接建立以后,就可以传输数据了。常用的系统调用有send()和recv()。send()调用用于客户数指定的已连接的数据报或流套接字上发送输出数据。recv()调用用于客户数指定的己连接的数据报或流套接字上接收输入数据。closes()关闭套接字,并释放分配给该套接字的资源;如果涉及一个打开的TCP连接,则该连接被释放。5.4.2视频数据发送视频数据发送主要包括:等待客户端的连接请求,创建图像采集线程,发送采集到的视频数据。发送流程见图5-8:图5.SEQ图5.\*ARABIC9视频数据发送流程该部分的网络编程涉及的是网络传输中面向连接的TCP协议[21][22]。TCP为应用程序提供可靠的通信连接,适合于一次传输大批数据的情况。并适用于要求得到响应的应用程序,TCP数据传输实现了从一个应用程序到另一个应用程序的数据传输。应用程序通过编程调用TCP并使用TCP服务,提供需要准备发送的数据,用来区分接收数据应用的目的地址和端口号。通常应用程序通过打开一个socket来使用TCP服务[23],TCP管理到其他socket的数据传递。可以说,通过IP的源/目的可以唯一地区分网络中两个设备的关联,通过socket的源/目的可以唯一地区分网络中两个应用程序的关联。(1)建立一个新的socket,并初始化套接字SOCK_STREAM:if((server_handle=socket(AF_INET,SOCK_STREAM,O))==-1)exit_fatal("ErroropeningsocketAbort!”);(2)实现socket的绑定:if(bind(server_handle,(structsockaddr*)&servadr,sizeof(structsockaddr))==-1)exit_fatal("errorbindsocket");(3)实现客户端请求的监听函数:if(1isten(serverhandle,MAXCONNECT)==-1)exit_fatal("DamnederrorswhenlistenAbort!");下面程序将接收来自客户端的请求:if((new_sock=accept(serv_sock,(structsockaddr*)&their_addr,&sin_size))==-1){continue;}客户端的请求响应后,接下来创建serverth线程来实现图像数据发送:Pthread_create(&server_th,NULL,(void*)service,&new_sock);当一个新的线程启动后,这个线程将负责把图像数据发送给用户。service函数正是视频数据网络发送的具体实现,需发送的数据包括帧信息头、帧数据两部分,发送数据可以使用write()来实现。(1)发送帧信息头:(函数返回值:成功;已写的字节数:-1:出错。)ret=write_sock(sock,(unsignedchar*)headerframe,sizeof(structframe_t));(2)发送帧数据:ret=write_sock(sock,(unsignedchar*)(videoIn.ptframe[frameout]+sizeof(structframe_t)),headerframe->size);
6.Android客户端的设计6.1Android平台简介2021年11月5日,C,oogle与其他33家制造商(包括摩托罗拉、宏达电、三星、LG)、芯片供应商、软硬件供应商、电信业者所联合组成的开放联盟(OpenHandsetAlliance,0HA),发布了名为Android的开放软硬件平台。Android是基于Linux内核的软件平台和操作系统。框架结构由5个部分组成,其核心为Linux内核,逐次向上是Android开发的Libraries(函数库)和AndroidRuntime(运行环境),以及搭配ApplicationFramework(应用程序框架)来开发各种不同的应用程序[24]。对于硬件开发商来说。Android是开放的平台,只要厂商有实力和能力就可以在此平台上自由添加特有的设备或功能,不受到操作系统的限制;对于开发者而言,Andwid是先进的平台,平台上的应用程序可兼容于各种型号的Android,免除为各种不同机型开发的困扰。Android平台支持各种先进的网络、绘图、3D处理能力,可以用来提供更好的用户体验。通过AndroidMar-ket将自己的应用程序销售给世界各地用户。对于用户来说,Android是一个用于的操作系统。只要用户申请了Coosle帐户,当想换时,可以在不同的厂牌同样使用Android操作系统平台的之间选择,并且很容易将比如通讯薄等个人资料转换到新上。6.2Android视频监视客户端整体设计方案Android客户端通过Socket与物联网服务端相连。主要流程为:视频流服务器->WIFI局域网/互联网->Android客户端。Android客户端的编程亦采用多线程编程:a,跟服务器建立连接,接收视频数据并放入全局缓存区。b,从缓存区取得视频数据,并将数据显示至ImageView组件中显示。c,监听界面中各个Button,并发送控制命令到服务器。6.3客户端视频数据接收的实现客户端视频数据的接受功能主要有两部分:一、建立网络通信,实现视频数据流的接受;二、实时显示接收到的图像数据(1)网络通信的建立图6.SEQ图6.\*ARABIC1Android客户端网络通信流程图(2)本系统是视频采集模块与Web服务器集成在一个系统板上实现的,所以口地址即为本地主机地址:3,端口号是与采集端设置的一样为:7070。有了P地址和端口号就可以创建Socket对象,并创建此Socket对象的输入、输出流。(3)分配接收缓冲区。整个系统处理的视频流是针对JPEG格式的,这里JPEG的像素点是按原始像素点4:1来压缩的,例如本系统支持最大的一幅640x480原始图片经压缩过大小为:640x480+4+8-1024=9.375KB左右;每帧的信息头固定为50个字节。所以在这里分配接收缓冲区大小为512×1024=64KB:byte[]buffer=newbyte[512*1024]。(4)读取图像头信息,确认图像数据的正确性intn=in.read(buffer,0,HDRLEN);//HDRLEN为信息头长度,设置为50对返回的长度进行判断,若相等,再对头信息中包含的约定字符进行判断,若正确就可以继续接收图像数据,不相等则重新接收头信息。(5)读取图像数据正确读取图像头信息后,就证明此次接收的视频数据流是正确的,接着就可以把头信息后的图像数据写入缓冲区,供播放显示:n=HDRLEN;r=in.read(buffer,n,buffer.1ength-n);6.4客户端界面设计远程视频实时监视的用户界面主要由Android的GUI系统实现,负责提供播放器和用户之间的交互接口,例如播放时的抓图、打开/关闭报警器、查看图片等功能。GUI系统由java语言框架和C语言框架组成,对于下层,GUI系统通过调用显示输入、输出设备的驱动将Android的软件系统和底层的硬件联系起来;对于上层,GUI系统提供了Java层次的绘图接口,Android的Java框架层调用这些绘图接口来构建各种UI元素。此外,Java应用程序层也可以调用这些绘图接口。图6.SEQ图6.\*ARABIC2Android客户端界面6.5视频客户端测试首先在PC机进行模拟测试,即在Android编译环境eclipse中将程序运行,通过模拟器测试成功。然后将程序移植到具备Android操作系统的里,利用WiFi无线网络连接服务器,测试结果验证了此视频客户端软件在功能上满足设计的基本需求。7.总结与展望7.1工作总结本文结合视频监控发展的方向,给出了一种基于Cortex-A8的视频监控系统设计方案,已Android平台开发客户端,并给出了系统的实现方法。在研究期间主要完成了以下工作:(1)研究了视频监控技术的现状及发展方向,给出了视频监控系统硬件平台的构建及软件总体框架设计,并对系统中的一些关键技术进行了分析和选型。(2)完成了嵌入式Linux平台的构建。首先建立交叉编译环境,接着介绍了BootLoader的基本概念和u-boot的启动过程,并针对本系统硬件对u-boot进行了修改和移植,然后编译和移植Linux内核,制作了YAFFS2文件系统。最后烧写uboot,下载内核和文件系统到开发板,实现了系统正常启动。(3)在Linux操作系统下开发了挂载在I²C的OV9650摄像头驱动程序,移植并加载了CMOS摄像头驱动到内核,在嵌入式Linux系统平台下实现了对摄像头的访问。(4)重点分析了linux内核的帧缓冲驱动框架,完成了LCD驱动开发,从而实现了视频流的本地显示。(5)实现了视频的采集、压缩、显示和传输。首先利用Video4Linux提供的接口函数,使用内存映射mmap方式实现了快速视频图像采集,提高了采集效率,最后讨论了在Linux下基于TCP/IP协议的socket编程,实现了视频数据的网络发送。(6)完成了Android客户端应用程序的编写,实现了客户端与服务器的成功连接,成功接收服务器发送来的视频数据,并进行的实时的显示,另外,完成了对报警器的控制,基本实现了远程视频监控。本系统采用了基于模块的设计方法,各个模块之间相互独立,增强了系统的健壮性和灵活性,当需要更换其中一个模块时其他模块并不需要做很大的改动,有利于系统的更新换代。7.2研究展望经过本系统的设计与实现工作,本人积累了嵌入式系统开发的相关经验,但由于时间和经验上的限制,系统在设计方面还有一些需要改进之处。具体说来主要有如下几点:(1)本系统上运行的嵌入式Linux目前使用的不是实时化的嵌入式Linux,将为了能够进一步提高应用任务执行的实时性,需要在该嵌入式Linux中加入实时模块。(2)在视频服务器上加入无线模块来达到视频数据的无线传输,也可在视频服务器与设备的连接方面,在目前的I²C、USB和RS232这些有线连接方式的基础上,增加诸如蓝牙、红外、zigbee等无线连接方式。(3)基于cortex-A8平台的优越性能,我们另外可扩展许多监控功能,譬如获取监控点的温度、适度、光照、三轴重力等信息。参考文献[1]刘富强.数字视频监控系统开发及应用[M].北京:机械工业出版社2021(3):15-1.[2]孟开元,车飞锋,曹庆年.基于嵌入式Web服务器的远程视频监控系统[J],中国科技信息,2021(20):93-94.[3]解天霞,李春葆.一种适合数字远程监控系统的网络体系设计[J].计算机工程与应用,2021(23):154-156.[4]杨建全,梁华,王成友.视频监控技术的发展与现状[J].自动化技术,2021(21):84-91.[5]何立民.嵌入式系统的定义与发展历史[J].单片机与嵌入式系统应用,2021(1):20-24.[6]杜春雷.ARM体系结构与编程[M].北京:清华大学出版社,2021.[7]百度百科.DM9000,2021.[8]詹荣开.嵌入式BootLoader技术内幕[EB/OL].http:www.embeded.crl.2021.12.[9]刘峥嵘,张智超,许振山.嵌入式Linux应用开发详解[M].北京:机械工业出版社,2021.[10]季志均,马文丽,陈虎.四种嵌入式实时操作系统关键技术分析[J].计算机应用研究,2021(9):4-8.[11]刘淼编著.嵌入式系统接口设计与Linux驱动程序开发[M].北京:北京航空航天大学出版社,2021.5[12]孙纪坤,张小全编著.嵌入式Linux系统开发技术详解~基于ARM[M].北京:人民邮电出版社,2021.[13]孙天泽,袁文菊,张海峰编著.嵌入式设计及Linux驱动开发指南[M].北京:电子工业出版社,2021.[14]LaurenceT.Yang.Embeddedsoftwareandsystems.Berlin:Stinger,2021.[15]ArlessandroRubini,JonathanCorbet著,魏永明等译.LINUX设备驱动程序(第三版)[M].0’REILLY&中国电力出版社,2021.[16]孙琼.嵌入式Linux应用程序开发详解[M].
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 出租车运输行业市场调研分析报告
- 便携式取暖器产品供应链分析
- 碗碟晾干架项目营销计划书
- 纸制筷子套细分市场深度研究报告
- 医用或兽医用培养细菌用介质产品供应链分析
- 医用减肥茶产品供应链分析
- 体育训练服务行业相关项目经营管理报告
- 电脑游戏操纵杆用充电器项目运营指导方案
- 物位变送器项目营销计划书
- 乐谱架产业链招商引资的调研报告
- 中国民歌介绍课件
- 《望天门山》-优质课件
- 高中数学必修一黄冈中学试卷(内含答案)
- 学写一种植物(三年级作文指导)课件
- 加油站安全承诺书
- 猪的呼吸道疾病课件
- (中职) 电子商务基础(第二版)教案
- 气温和气温的分布 详细版课件
- 汽车品牌保时捷课件
- 人教版数学三年级上册《分数的初步认识》课件 (共7张PPT)
- 5000吨每年聚丙烯酰胺工艺流程图
评论
0/150
提交评论