日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 运维知识 > linux >内容正文

linux

Video4Linux

發(fā)布時(shí)間:2024/9/5 linux 63 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Video4Linux 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
 Video4Linux(簡(jiǎn)V4L)是Linux中關(guān)于視頻設(shè)備的內(nèi)核驅(qū)動(dòng),它為針對(duì)視頻設(shè)備的應(yīng)用程序編 程提供一系列接口函數(shù),這些視頻設(shè)備包括現(xiàn)今市場(chǎng)上流行的TV卡、視頻捕捉卡和USB攝像頭等。對(duì)于USB口攝像頭,其驅(qū)動(dòng)程序中需要提供基本的I/O操 作接口函數(shù)open、read、write、close的實(shí)現(xiàn)。對(duì)中斷的處理實(shí)現(xiàn),內(nèi)存映射功能以及對(duì)I/O通道的控制接口函數(shù)ioct1的實(shí)現(xiàn)等,并把 它們定義在struct file_operations中。這樣當(dāng)應(yīng)用程序?qū)υO(shè)備文件進(jìn)行諸如open、close、read、write等系統(tǒng)調(diào)用操作時(shí),Linux內(nèi)核將通 過file_operations結(jié)構(gòu)訪問驅(qū)動(dòng)程序提供的函數(shù)。例如,當(dāng)應(yīng)用程序?qū)υO(shè)備文件執(zhí)行讀操作時(shí),內(nèi)核將調(diào)用file_operations結(jié)構(gòu) 中的read函數(shù)。在系統(tǒng)平臺(tái)上對(duì)USB口數(shù)碼攝像頭驅(qū)動(dòng),首先把USB控制器驅(qū)動(dòng)模塊靜態(tài)編譯進(jìn)內(nèi)核,使平臺(tái)中支持USB接口,再在需要使用攝像頭采集 時(shí),使用insmode動(dòng)態(tài)加載其驅(qū)動(dòng)模塊,這樣攝像頭就可正常工作了,接著進(jìn)行了下一步對(duì)視頻流的采集編程。

程序中定義的數(shù)據(jù)結(jié)構(gòu)
struct voide_capability grab_cap;
struct voide_picture grab_pic;
struct voide_mmap grab_buf;
struct voide_mbuf grab_vm;
這些數(shù)據(jù)結(jié)構(gòu)都是由Video4Linux支持的,它們的用途如下:
*video_capability包含攝像頭的基本信息,例如設(shè)備名稱、支持的最大最小分辨率、信號(hào)源信息等,分別對(duì)應(yīng)著結(jié)構(gòu)體中成員變量name [32]、maxwidth、maxheight、minwidth、minheight、channels(信號(hào)源個(gè)數(shù))、type等;
*voide_picture包含設(shè)備采集圖像的各種屬性,如brightness(亮度)、hue(色調(diào))、contrast(對(duì)比度)、whiteness(色度)、depth(深度)等;
*video_mmap用于內(nèi)存映射;
*voido_mbuf利用mmap進(jìn)行映射的幀信息,實(shí)際上是輸入到攝像頭存儲(chǔ)器緩沖中的幀信息,包括size(幀的大小)、frames(最多支持的幀數(shù))、offsets(每幀相對(duì)基址的偏移)。
程序中用到的主要系統(tǒng)調(diào)用函數(shù)有:open("/dev/voideo0",int flags)、close(fd)、mmap(void *start,size_t length,int prot,int flags,int fd,off_t offset)、munmap(void *start,size_tlength)和ioctl(int fd,int cmd,…)。
前面提到Linux系統(tǒng)中把設(shè)備看成設(shè)備文件,在用戶空間可以通過標(biāo)準(zhǔn)的I/O系統(tǒng)調(diào)用函數(shù)操作設(shè)備文件,從而達(dá)到與設(shè)備通信交互的目的。當(dāng)然,在設(shè)備驅(qū)動(dòng)中要提供對(duì)這些函數(shù)的相應(yīng)支持。這里說明一下ioctl(int fd,int cmd,…)函數(shù),它在用戶程序中用來控制I/O通道,其中,fd代表設(shè)備文件描述符,cmd代表用戶程序?qū)υO(shè)備的控制命令,省略號(hào)一般是一個(gè)表示類型長(zhǎng)度的參數(shù),也可沒有。
(2)采集程序?qū)崿F(xiàn)過程
首先打開視頻設(shè)備,攝像頭在系統(tǒng)中對(duì)應(yīng)的設(shè)備文件為/dev/video0,采用系統(tǒng)調(diào)用函數(shù)grab_fd=open("/dev/video0", O_RDWR),grab_fd是設(shè)備打開后返回的文件描述符(打開錯(cuò)誤返回-1),以后的系統(tǒng)調(diào)用函數(shù)就可使用它來對(duì)設(shè)備文件進(jìn)行操作了。接著,利用 ioct1(grab_fd,VIDIOCGCAP,&grab_cap)函數(shù)讀取struct video_capability中有關(guān)攝像頭的信息。該函數(shù)成功返回后,這些信息從內(nèi)核空間拷貝到用戶程序空間grab_cap各成員分量中,使用 printf函數(shù)就可得到各成員分量信息,例如printf("maxheight=%d",grab_fd.maxheight)獲得最大垂直分辨率的 大小。不規(guī)則用ioct1(grab_fd,VIDIOCGPICT,&grab_pic)函數(shù)讀取攝像頭緩沖中voideo_picture信 息。在用戶空間程序中可以改變這些信息,具體方法為先給分量賦新值,再調(diào)用VIDIOCSPICT ioct1函數(shù),例如:
grab_fd.depth=3;
if(ioct1(grab_fd,VIDIOCSPICT,&grab_pic)<0)
{perror("VIDIOCSPICT");return -1;};
完成以上初始化設(shè)備工作后,就可以對(duì)視頻圖像截取了,有兩種方法:一種是read()直接讀取;另外一種mmap()內(nèi)存映射。Read()通過內(nèi)核緩沖 區(qū)來讀取數(shù)據(jù);而mmap()通過把設(shè)備文件映射到內(nèi)存中,繞過了內(nèi)核緩沖區(qū),最快的磁盤訪問往往還是慢于最慢的內(nèi)存訪問,所以mmap()方式加速了 I/O訪問。另外,mmap()系統(tǒng)調(diào)用使得進(jìn)程之間通過映射同一文件實(shí)現(xiàn)共享內(nèi)存,各進(jìn)程可以像訪問普通內(nèi)存一樣對(duì)文件進(jìn)行訪問,訪問時(shí)只需要使用指針 而不用調(diào)用文件操作函數(shù)。因?yàn)閙map()的以上優(yōu)點(diǎn),所以在程序?qū)崿F(xiàn)中采用了內(nèi)存映射方式,即mmap()方式。
利用mmap()方式視頻裁取具體進(jìn)行操作如下。
①先使用ioct1(grab_fd,VIDIOCGMBUF,&grab_vm)函數(shù)獲得攝像頭存儲(chǔ)緩沖區(qū)的幀信息,之后修改voideo_mmap中的設(shè)置,例如重新設(shè)置圖像幀的垂直及水平分辨率、彩色顯示格式。可利用如下語句
grab_buf.height=240;
grab_buf.width=320;
grab_buf.format=VIDEO_PALETTE_RGB24;
②接著把攝像頭對(duì)應(yīng)的設(shè)備文件映射到內(nèi)存區(qū),具體使用grab_data=(unsigned char*)mmap(0,grab_vm.size,PROT_READ|PROT_WRITE,MAP_SHARED,grad_fd,0)操作。這 樣設(shè)備文件的內(nèi)容就映射到內(nèi)存區(qū),該映射內(nèi)容區(qū)可讀可寫并且不同進(jìn)程間可共享。該函數(shù)成功時(shí)返回映像內(nèi)存區(qū)的指針,挫敗時(shí)返回值為-1。
下面對(duì)單幀采集和連續(xù)幀采集進(jìn)行說明:
*單幀采集。在上面獲取的攝像頭存儲(chǔ)緩沖區(qū)幀信息中,最多可支持的幀數(shù)(frames的值)一般為兩幀。對(duì)于單幀采集只需設(shè)置 grab_buf.frame=0,即采集其中的第一幀,使用ioctl(grab_fd,VIDIOCMCAPTURE,&grab_buf) 函數(shù),若調(diào)用成功,則激活設(shè)備真正開始一幀圖像的截取,是非阻塞的。接著使用ioct1(grab_fd,VIDIOCSYNC,&frame) 函數(shù)判斷該幀圖像是否截取完畢,成功返回表示截取完畢,之后就可把圖像數(shù)據(jù)保存成文件的形式。
*連續(xù)幀采集。在單幀的基礎(chǔ)上,利用grab_fd.frames值確定采集完畢攝像頭幀緩沖區(qū)幀數(shù)據(jù)進(jìn)行循環(huán)的次數(shù)。在循環(huán)語句中,也是使用VIDIOCMCCAPTURE ioct1和VIDIOCSYNC ioctl函數(shù)完成每幀截取,但要給采集到的每幀圖像賦地址,利用語句buf=grab_data+grab_vm.offsets[frame],然后保存文件的形式。若要繼續(xù)采集可再加一個(gè)外循環(huán),在外循環(huán)語句只要給原來的內(nèi)循環(huán)再賦frame=0即可。
4 小結(jié)
筆者最后在宿主機(jī)PC上使用交叉編譯器編譯鏈接連續(xù)幀采集程序(以雙幀采集為例并保存成bmp文件文件形式)使之生成可執(zhí)行代碼,并完成了向目標(biāo)平臺(tái)的移 植。為了進(jìn)一步觀察采集的圖像效果,筆者在目標(biāo)平臺(tái)帶網(wǎng)絡(luò)支持的基礎(chǔ)上,編寫了一個(gè)簡(jiǎn)單的網(wǎng)絡(luò)通信程序,把采集到并保存為bmp的圖像文件通過網(wǎng)絡(luò)傳輸?shù)?PC機(jī)上進(jìn)行顯示,把采集到并保存為bmp的圖像文件通過網(wǎng)絡(luò)傳輸?shù)絇C機(jī)上進(jìn)行顯示,通過對(duì)效果的分析,再回到采集程序中重新設(shè)置 video_picture中的信息,如亮度、對(duì)比度等和voide_mmap中的分辨率,重新移植以達(dá)到最好效果為準(zhǔn)。

在圖1中的嵌入式系統(tǒng)平臺(tái)上,應(yīng)用本文所述方法完成視頻采集工作,再加上相關(guān)的視頻處理并接入網(wǎng)絡(luò),就構(gòu)成了一個(gè)智能終端設(shè)備,可用于工廠、銀行及小區(qū)等場(chǎng)合全天候的智能監(jiān)控,具有廣闊的市場(chǎng)和應(yīng)用前景。


http://hi.baidu.com/doing4who/blog/item/b1c41023bf4739519922ed71.html

總結(jié)

以上是生活随笔為你收集整理的Video4Linux的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。