2410摄像头问题

近日有不少网友问me 2410上摄像头驱动加载,那我就将我的方法贴出来。嘿嘿。若有不对之处请大家多多指正哦。
  驱动加载步骤:(模块加载方式)
1.修改/driver/usb/ov511.c中ov51x_set_default_params函数,改ov511->frame[i].format = VIDEO_PALETTE_RGB24; 
为ov511->frame[i].format = VIDEO_PALETTE_RGB565;当然了这是为了在LCD上显示才这样做的(LCD是16位显示的)。
2.在arm linux的kernel目录下make menuconfig,首先<*>选择Multimedia device->下的Video for linux,然后在usb support->目录下<*>选择support for usb和<M>选择usb camera ov511 support,保存退出。
3.Make dep;make zImage;make modules然后就在/driver/usb下生成ov511.o,同时生成的zImage自动放在/tftpboot下了。
4.然后用新内核启动板子后insmod ov511.o就可以成功加载啦。
----------------
模块加载中的一些问题的总结,现将我遇到的贴出来。以后慢慢加喽。
1.insmod和modprobe间的一个区别试后者不会在当前目录中查找模块,它只在/lib/modules下的缺省目录下查找,这是因为该程序只是一个系统实用例程,不是一个交互工具。可以通过在/etc/modules.conf中指定自己的目录,来把它们加到缺省目录集中。
2.如果插入模块ov511.o时,出现以下信息:
Ov511.o:unresolved symbol video********之类的,说明还有其它模块videodev.o没有加啊。
3.出现错误:ov511.o:couldn’t find the kernel version this modules was compiled for。这是试图插入一个不是可装入模块的目标文件。因为在内核配置阶段,是把ov511模块静态加到内核中的,虽然看起来和可装入模块的文件名ov511.o完全一样,但是不能用insmod命令加入。
----------------------------------
态编译到内核里面就是按我们文档直接操作就是了。
编出来的驱动就打到最后生成的zImage里面了,下载到板子的SDRAM中go 30008000跑起来后插入摄像头进行测试即可。
但这样显然不如动态MODULES加载的方式方便嘛,每次都要下载整个的内核。
-----------------------------
spac5xx摄像头驱动的测试实际上很简单,呵呵,cat /dev/video0 > pic.jpg
然后把板子上的文件ftp到pc机中,随便用看图软件看看就知道了。还有,那个网站上实际上提供了基于以太网的测试程序,自己移植一下,很简单
-----------------------------
今天实现了接多个ov511摄像头。方法如下:买一个usb hub(我的是四口的)接到开发板的usb host上,理论上应该可以接四个摄像头,可是我只有两个,嘿嘿,所以只接两个。cat /proc/devices可以知道video capture device的major是81,再ls –l /dev看到video0的次设备号是0。两个摄像头当然要两个设备号啦,所以mknod /dev/video1 c 81 1,如果接4个,就mknod /dev/video2 c 81 2,mknod /dev//video3 c 81 3。依次类推。
  在应用程序中,一个open(dev/video0),一个open(/dev/video1)就可以测试了,我用cam2fb通过测试。两个不能同时运行,否则出现usb schedule overrun。
--------------------------------------
接HUB但实际还是就一个USB HOST口,肯定不能同时打开两个USB 摄像头嘛
-----------------
先说明一下,我的中芯微的摄像头的驱动,应用程序都是从http://mxhaard.free.fr/下的。待会就不说明了。
针对embeded环境,有专门的patch,我用的是usb-2.4.31LE06.patch。
(1)把它放到/HHARM9-EDU/kernel/driver/usb下,解压,打补丁。就会在此目录下看到spca5xx文件夹了。可能会有一些错误,我的错误是在Makefile和config.in文件中,根据它的提示,进行相应的修改即可。Patch时会将修改方法写到Makefile.rej和config.in.rej文件中,把这两个文件里的内容加到Makefile和config.in中就行了。
(2)编译内核,进入/HHARM9-EDU/kernel,make menuconfig。我采用和上面介绍的ov511驱动的方法一样,动态加载。(M)选中SPCA5XX这一项。
(3)make dep;make zImage;make modules。就会在/HHARM9-EDU/kernel/driver/usb/spca5xx中生成spca5xx.o,spcadecoder.o,spca_core.o啦。这就是我们要的驱动。
(4)用新内核启动,insmod这三个.o文件,摄像头就加载成功啦。
应用程序servfox和spcaview的使用方法:
(1)Spcaview既可以做采集端,也可以做接收端。不过移植有点复杂^_^。所以采用servfox做为采集端,移植到arm上。修改servfox里的Makefile文件,很简单,只用将gcc改成/opt/host/armv41/bin/armv41-unknown-linux-gcc即可。Make一下,就可以在板上运行啦。
(2)Spcaview直接make即可生成可执行文件spcaview。
(3)现在就可以工作啦。在开发板上servfox –d /dev/video0 –s 640x480 –w 192.168.2.122:7070
在PC上,spcaview –w 192.168.2.120:7070就可以看到摄像头采集来的图片啦。Servfox和spcaview还有很多选项,可以通过spcaview –h 和servfox –h查阅。
^_^。有时间把spcaview和servfox的源码好好研究一下。改成从无线方式发送。

---------------------------------------
实现了用程序控制两个摄像头轮流采集啦。说说我的思路,写三个程序。两个用于发送端,一个用于接收端接收显示图像。发送端的两个程序一个是主程序,不停的循环,用于生成子进程来execl图像采集发送程序,采集到一定帧数就退出。每次生成的子进程,传递不同的设备名,也就是/dev/video0或/dev/video1。也就是父子进程通讯啦
------------------------------------
可以实现在一个usb hub上接一个摄像头,一个u盘,然后一边采集一边压缩成jpeg图像保存到u盘里啦
---------------------------------------
前阶段我所说的ov511(网眼3000)在我自己写的程序以240x320方式下截图花屏,是因为ov511不支持此分辨率,已经在pc上用其他视频程序证实。现在我的程序可以良好的工作在240x240模式以RGB565方式输出图像,并且直接显示在液晶屏上。屏幕下方一段240x80的空间用来显示一些信息(说白了就是显示些字),因为摄像头模块只是我所要做的一部分。

最近刚新买了一个中星微芯片zc0301p的摄像头,碰到了一些问题,如下:
PC平台:装了3系统,SUSE Linux 9.3(2.6核),Red Hat Linux 9(2.4.20-8),Windows XP
嵌入式平台:华恒HHARM9-EDU-R2

1.首先在嵌入式平台试了spca5xx-LE驱动,可以驱动。移植的Servfox可以工作,spcaview可以接收到图像,但会掉帧。但这还不是首要问题。

2.用spca5xx-LE驱动时,我自己写的程序无法使用,运行到设置图像格式(RGB565或RGB24)时出错,说不支持此参数。原因在于:(摘自驱动程序主页http://mxhaard.free.fr/spca5le.html)
The spca5xx-LE design is very different from the spca5xx full package(LE版的驱动和完全版的差很多)。
The memory in use are the most smaller as possible(LE版的驱动会尽量减少内存的使用)
The spcadecoder is reduce and only raw jpeg webcam are used.(驱动模块只支持输出原始jpeg格式,my god!)

3.明显LE的驱动不符合我的要求。我所要做的是:我已经有了自己的摄像头应用程序,只想在驱动方面多支持一些市面上常用摄像头。(如果只能支持现在已经基本灭绝的几款摄像头,那还有什么意义,不过实在不行也没办法就是了)

4.那么只能移植完整版的驱动到实验箱了。问题来了,按照spca5xx完整版的INSTALL安装指南,在SuSE 9.3上轻松编译安装(也就只是make;make install而已)。用我自己写的程序测试可以驱动并成功截图,但分辨率不支持240x240(shit!难道我还得改实验箱上弄好的程序),只支持640x480和320x240,并且240x320也不支持。难道要把输出的320x240图像,旋转90度,再显示在lcd上,那可真够麻烦的。

5.试着做了一下:安装指南里并没有讲如何移植,难道只要在编译的时候指定gcc为armv4l-unknown-gcc就可以?(试过,失败)或者像LE版驱动一样,复制到usb驱动文件夹,建个spca5xx文件夹,修改makefile和config.in?(试过,仍然不行,make modules可以生成驱动模块,但insmod时出错,说找不到支持的核心版本),谁能给出一个详细的移植过程(要的是完整版的spca5xx驱动)

6.在Red Hat9上编译失败(解决办法在后面,但是我并没有去试,因为我的SuSE已经可以用了),原因在于:
这里引用一个大牛的说法(原文连接http://blog.wulei.net/2006/04/10/62.html#more-62):"RedHat 的内核是非标准内核,他将 remap_page_range从4个参数擅自更改为5个参数。然而这5个参数的remmap_page_range是内核2.5.0中使用的 ,2.6中也已经弃用了。换句话说,就是RedHat linux己制造了不兼容!!!感觉这种手段和xxx何其相似!!!在此严重鄙视一下Redhat.也就是如果你选择了redhat的产品,要么掏钱去请求其服务,要么自己解决问题。而隔绝了和其他linux社区的帮助。于是我决定抛弃其提供的内核,升级到标准内核。于是,开始疯狂的下载内核,编译内核,试图通过这种方式来解决这个不兼容的问题。我尝试 redhat自己的2.4.21的更高版本2.4.21-40.EL, 但是编译spca之后发现出现的错误更加多, 说明现在redhat自己的内核已经离标准愈来愈远了。太息之余,我想试试标准的内核能否工作。我于是在kernel.org下载并编译了2.4.32和2.4.31,这两个内核都可以完全正确的编译spca5xx 驱动。但是严重的是,我的其他软件变的非常不稳定,而且系统自带的mysql和我的XFree86完全启动不了。这再次印证了RedHat的非标准作风。证实了其试图将用户帮定在其平台的野心。我决心以后一定皈依到debian门下。但是我目前还得想办法解决。"

请继续看:"通过阅读我有了一个重要的发现在05年初期的开发版中,很多人都说只要将RH9_REMMAP宏定义打开就可以了。于是我决定试试这个时候的版本。于是下载了spca5xx20050111版本,结果出乎我意料,真的可以运行了!!!但是,效果非常差。没有我实验的在2.6内核下的那么好。但是我终于有了一个可用的版本。现在有好的开始了。我终于能找到门路了。我只要从这个版本开始跟踪开发,就能知道到底是什么导致了在我们的系统上不能成功。于是我陆续下载了20050319和20050419,结果发现前者是可以运行的,后者开始出错。好了,我现在十分满意,通过对这两个版本的比较,我就能搞清楚问题所在了。"

原因真相大白:"于是我通过emacs的ediff对比阅读了这两个版本的spca5xx.c文件。原来不光是remap_page_range这一个函数的问题,而是围绕这个问题的一些程序的架构。估计是从20050419以后由于大部分人都从redhat 9转到了Fedra结果着个问题就不重要了,因此该驱动在redhat下的分支已经没有人维护了,才导致了代码的不兼容。"

解决方法:此大牛提供了一个patch,放在最后吧,需要注意的是他的系统是redhat企业版,内核:2.4.21-4.EL i686,不过spca5xx在sourceforge也提供了它的解决方法,如下:
Q:I'm using Redhat 9, and the driver won't compile!(我用Redhat9,但驱动无法成功编译)
A:This problem is caused by the fact that Redhat has tweaked the default kernel included in Redhat 9(redhat公司修改了默认的内核), to solve this problem get different kernel(想要解决这个问题,要么下载新的内核(源代码)), or do this:(要么只能……自己看吧)
Download the CVS version of the driver, and add #define RH9_REMAP 1 to the top of spca50x.c. then compile and install. 
原文连接http://spca50x.sourceforge.net/spca50x.php?page=faq#5

=========================================================================
总结如下:
1.我需要完整版的spca5xx驱动详细的移植过程(如果你有耐心看到这里,就一定有耐心再写一篇文章出来,大侠们,快点跳出来吧)
2.spca5xx-LE驱动只支持输出jpeg格式图像
3.许多2.6核的linux系统编译spca5xx完整版会很顺利(有些甚至直接就支持)
4.Red hat 9编译完整版spca5xx时,版本号在20050319之前的可能不会出错(但效果很差),而之后的会出错。
出错有解决办法(并且这些方法没有经过我自己的验证,所以不保证能用):第一种方法:去www.kernel.org下载官方的核心源代码编译。第二种方法:spca5xx开发站点提供的做法Download the CVS version of the driver, and add #define RH9_REMAP 1 to the top of spca50x.c. then compile and install.  第三种方法:把下面的内容(源自http://blog.wulei.net/2006/04/10/62.html#more-62)存成spca5xx20060402.patch,然后将该文件放在解压后的spca5xx20060402/目录下,执行patch -p1 < spca5xx20060402.patch
========================================================================
diff -rc spca5xx-20060402/drivers/usb/spca5xx.c spca5xx-20060402-wu/drivers/usb/spca5xx.c
*** spca5xx-20060402/drivers/usb/spca5xx.c2006-04-03 03:33:50.000000000 +0800
--- spca5xx-20060402-wu/drivers/usb/spca5xx.c2006-04-10 18:05:48.000000000 +0800
***************
*** 81,86 ****
--- 81,91 ----
#endif

//#define RH9_REMAP 1
+ #if defined(RHEL3)
+ #ifndef  RH9_REMAP
+ #define RH9_REMAP 1
+ #endif
+ #endif

#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 0)
#include "spcaCompat.h"
***************
*** 1174,1180 ****
{
void *mem;
unsigned long adr;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 4, 23)
unsigned long page;
#endif
size = PAGE_ALIGN(size);
--- 1179,1185 ----
{
void *mem;
unsigned long adr;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,23) && !defined(RHEL3)
unsigned long page;
#endif
size = PAGE_ALIGN(size);
***************
*** 1188,1194 ****
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 68)
SetPageReserved(vmalloc_to_page((void *) adr));
#else
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 4, 23)
mem_map_reserve(vmalloc_to_page((void *) adr));
#else
page = kvirt_to_pa(adr);
— 1193,1199 —-
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 68)
SetPageReserved(vmalloc_to_page((void *) adr));
#else
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,23) || defined(RHEL3)
mem_map_reserve(vmalloc_to_page((void *) adr));
#else
page = kvirt_to_pa(adr);
***************
*** 1205,1211 ****
static void rvfree(void *mem, unsigned long size)
{
unsigned long adr;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 4, 23)
unsigned long page;
#endif
if (!mem)
--- 1210,1216 ----
static void rvfree(void *mem, unsigned long size)
{
unsigned long adr;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,23) && !defined(RHEL3)
unsigned long page;
#endif
if (!mem)
***************
*** 1216,1222 ****
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 68)
ClearPageReserved(vmalloc_to_page((void *) adr));
#else
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 4, 23)
mem_map_unreserve(vmalloc_to_page((void *) adr));
#else
page = kvirt_to_pa(adr);
— 1221,1227 —-
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 68)
ClearPageReserved(vmalloc_to_page((void *) adr));
#else
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,23) || defined(RHEL3)
mem_map_unreserve(vmalloc_to_page((void *) adr));
#else
page = kvirt_to_pa(adr);
***************
*** 3869,3875 ****
spin_unlock_irqrestore(&spca50x->v4l_lock, flags);
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
static int spca5xx_open(struct inode *inode, struct file *file)
{
struct video_device *vdev = video_devdata(file);
— 3874,3880 —-
spin_unlock_irqrestore(&spca50x->v4l_lock, flags);
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
static int spca5xx_open(struct inode *inode, struct file *file)
{
struct video_device *vdev = video_devdata(file);
***************
*** 3912,3918 ****
spca5xx_setFrameDecoder(spca50x);

spca50x->user++;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
file->private_data = vdev;
#endif
err = spca50x_init_isoc(spca50x);
— 3917,3923 —-
spca5xx_setFrameDecoder(spca50x);

spca50x->user++;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
file->private_data = vdev;
#endif
err = spca50x_init_isoc(spca50x);
***************
*** 3922,3928 ****
spca5xx_kill_isoc(spca50x);
up(&spca50x->lock);
spca5xx_dealloc(spca50x);
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
file->private_data = NULL;
#endif
goto out2;
— 3927,3933 —-
spca5xx_kill_isoc(spca50x);
up(&spca50x->lock);
spca5xx_dealloc(spca50x);
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
file->private_data = NULL;
#endif
goto out2;
***************
*** 3978,3984 ****
}
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
static int spca5xx_close(struct inode *inode, struct file *file)
{

— 3983,3989 —-
}
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) ||defined(RHEL3)
static int spca5xx_close(struct inode *inode, struct file *file)
{

***************
*** 4017,4023 ****
MOD_DEC_USE_COUNT;
#endif

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
file->private_data = NULL;
return 0;
#endif
— 4022,4028 —-
MOD_DEC_USE_COUNT;
#endif

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
file->private_data = NULL;
return 0;
#endif
***************
*** 4037,4043 ****
return 0;
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
static int
spca5xx_do_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
void *arg)
— 4042,4048 —-
return 0;
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
static int
spca5xx_do_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
void *arg)
***************
*** 4058,4064 ****
switch (cmd) {
case VIDIOCGCAP:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_capability *b = arg;
#else
struct video_capability j;
— 4063,4069 —-
switch (cmd) {
case VIDIOCGCAP:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_capability *b = arg;
#else
struct video_capability j;
***************
*** 4076,4082 ****

b->minwidth = spca50x->minwidth;
b->minheight = spca50x->minheight;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22)
if (copy_to_user(arg, b, sizeof(struct video_capability)))
return -EFAULT;
#endif
--- 4081,4087 ----

b->minwidth = spca50x->minwidth;
b->minheight = spca50x->minheight;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22) && !defined(RHEL3)
if (copy_to_user(arg, b, sizeof(struct video_capability)))
return -EFAULT;
#endif
***************
*** 4085,4091 ****
}
case VIDIOCGCHAN:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_channel *v = arg;
#else
struct video_channel k;
— 4090,4096 —-
}
case VIDIOCGCHAN:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_channel *v = arg;
#else
struct video_channel k;
***************
*** 4148,4154 ****
v->flags = 0;
v->tuners = 0;
v->type = VIDEO_TYPE_CAMERA;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22)
if (copy_to_user(arg, v, sizeof(struct video_channel)))
return -EFAULT;
#endif
--- 4153,4159 ----
v->flags = 0;
v->tuners = 0;
v->type = VIDEO_TYPE_CAMERA;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22) && !defined(RHEL3)
if (copy_to_user(arg, v, sizeof(struct video_channel)))
return -EFAULT;
#endif
***************
*** 4163,4169 ****
of video_channel is an int channel number
and we just ignore the rest
*/
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_channel *v = arg;
#else
struct video_channel k;
— 4168,4174 —-
of video_channel is an int channel number
and we just ignore the rest
*/
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_channel *v = arg;
#else
struct video_channel k;
***************
*** 4184,4190 ****
}
case VIDIOCGPICT:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_picture *p = arg;
#else
struct video_picture p1;
— 4189,4195 —-
}
case VIDIOCGPICT:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) ||defined(RHEL3)
struct video_picture *p = arg;
#else
struct video_picture p1;
***************
*** 4327,4333 ****
}
}

! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22)
if (copy_to_user(arg, p, sizeof(struct video_picture)))
return -EFAULT;
#endif
--- 4332,4338 ----
}
}

! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22) && !defined(RHEL3)
if (copy_to_user(arg, p, sizeof(struct video_picture)))
return -EFAULT;
#endif
***************
*** 4337,4343 ****
case VIDIOCSPICT:
{
int i;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_picture *p = arg;
#else
struct video_picture p1;
— 4342,4348 —-
case VIDIOCSPICT:
{
int i;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) ||defined(RHEL3)
struct video_picture *p = arg;
#else
struct video_picture p1;
***************
*** 4555,4561 ****
}
case VIDIOCSCAPTURE:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_capture *vc = arg;
#else
struct video_capture vc1;
— 4560,4566 —-
}
case VIDIOCSCAPTURE:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) ||defined(RHEL3)
struct video_capture *vc = arg;
#else
struct video_capture vc1;
***************
*** 4574,4580 ****
case VIDIOCSWIN:
{
int result;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_window *vw = arg;
#else
struct video_window vw1;
— 4579,4585 —-
case VIDIOCSWIN:
{
int result;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_window *vw = arg;
#else
struct video_window vw1;
***************
*** 4632,4638 ****
}
case VIDIOCGWIN:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_window *vw = arg;
#else
struct video_window vw1;
— 4637,4643 —-
}
case VIDIOCGWIN:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_window *vw = arg;
#else
struct video_window vw1;
***************
*** 4647,4653 ****
vw->flags = 0;

PDEBUG(4, “VIDIOCGWIN: %dx%d”, vw->width, vw->height);
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22)
if (copy_to_user(arg, vw, sizeof(struct video_capture)))
return -EFAULT;
#endif
--- 4652,4658 ----
vw->flags = 0;

PDEBUG(4, “VIDIOCGWIN: %dx%d”, vw->width, vw->height);
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22) && !defined(RHEL3)
if (copy_to_user(arg, vw, sizeof(struct video_capture)))
return -EFAULT;
#endif
***************
*** 4656,4662 ****
}
case VIDIOCGMBUF:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_mbuf *vm = arg;
#else
struct video_mbuf vm1;
— 4661,4667 —-
}
case VIDIOCGMBUF:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) ||defined(RHEL3)
struct video_mbuf *vm = arg;
#else
struct video_mbuf vm1;
***************
*** 4671,4677 ****
for (i = 0; i < SPCA50X_NUMFRAMES; i++) {
vm->offsets[i] = MAX_DATA_SIZE * i;
}
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22)
if (copy_to_user(arg, vm, sizeof(struct video_mbuf)))
return -EFAULT;
#endif
--- 4676,4682 ----
for (i = 0; i < SPCA50X_NUMFRAMES; i++) {
vm->offsets[i] = MAX_DATA_SIZE * i;
}
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22) && !defined(RHEL3)
if (copy_to_user(arg, vm, sizeof(struct video_mbuf)))
return -EFAULT;
#endif
***************
*** 4681,4687 ****
case VIDIOCMCAPTURE:
{
int ret, depth;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_mmap *vm = arg;
#else
struct video_mmap vm1;
— 4686,4692 —-
case VIDIOCMCAPTURE:
{
int ret, depth;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_mmap *vm = arg;
#else
struct video_mmap vm1;
***************
*** 4816,4822 ****
case VIDIOCSYNC:
{
int ret;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
unsigned int frame = *((unsigned int *) arg);
#else
unsigned int frame;
— 4821,4827 —-
case VIDIOCSYNC:
{
int ret;
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) ||defined(RHEL3)
unsigned int frame = *((unsigned int *) arg);
#else
unsigned int frame;
***************
*** 4875,4881 ****
}
case VIDIOCGFBUF:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_buffer *vb = arg;
#else
struct video_buffer vb1;
— 4880,4886 —-
}
case VIDIOCGFBUF:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_buffer *vb = arg;
#else
struct video_buffer vb1;
***************
*** 4883,4889 ****
#endif
memset(vb, 0, sizeof(struct video_buffer));
vb->base = NULL;/* frame buffer not supported, not used */
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22)
if (copy_to_user(arg, vb, sizeof(struct video_buffer)))
return -EFAULT;
#endif
--- 4888,4894 ----
#endif
memset(vb, 0, sizeof(struct video_buffer));
vb->base = NULL;/* frame buffer not supported, not used */
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22) && !defined(RHEL3)
if (copy_to_user(arg, vb, sizeof(struct video_buffer)))
return -EFAULT;
#endif
***************
*** 4892,4898 ****
}
case SPCAGVIDIOPARAM:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_param *vp = arg;
#else
struct video_param vp1;
— 4897,4903 —-
}
case SPCAGVIDIOPARAM:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_param *vp = arg;
#else
struct video_param vp1;
***************
*** 4901,4907 ****
vp->autobright = (__u8) spca50x->autoexpo;
vp->quality = (__u8) spca50x->qindex;
vp->time_interval = (__u16) spca50x->dtimes;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22)
if (copy_to_user(arg, vp, sizeof(struct video_param)))
return -EFAULT;
#endif
--- 4906,4912 ----
vp->autobright = (__u8) spca50x->autoexpo;
vp->quality = (__u8) spca50x->qindex;
vp->time_interval = (__u16) spca50x->dtimes;
! #if LINUX_VERSION_CODE < KERNEL_VERSION(2,4,22) && !defined(RHEL3)
if (copy_to_user(arg, vp, sizeof(struct video_param)))
return -EFAULT;
#endif
***************
*** 4910,4916 ****

case SPCASVIDIOPARAM:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
struct video_param *vp = arg;
#else
struct video_param vp1;
— 4915,4921 —-

case SPCASVIDIOPARAM:
{
! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
struct video_param *vp = arg;
#else
struct video_param vp1;
***************
*** 4957,4963 ****
return 0;
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
static int
spca5xx_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
unsigned long arg)
— 4962,4968 —-
return 0;
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) ||defined(RHEL3)
static int
spca5xx_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
unsigned long arg)
***************
*** 4974,4987 ****
#endif
rc = video_usercopy(inode, file, cmd, arg, spca5xx_do_ioctl);
#if 0
! /* see 7 lines up */ */
up(&spca50x->lock);
#endif
return rc;
}
#endif

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
static ssize_t
spca5xx_read(struct file *file, char *buf, size_t cnt, loff_t * ppos)
{
— 4979,4992 —-
#endif
rc = video_usercopy(inode, file, cmd, arg, spca5xx_do_ioctl);
#if 0
! /* see 7 lines up */
up(&spca50x->lock);
#endif
return rc;
}
#endif

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)||defined(RHEL3)
static ssize_t
spca5xx_read(struct file *file, char *buf, size_t cnt, loff_t * ppos)
{
***************
*** 5089,5095 ****
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
static int spca5xx_mmap(struct file *file, struct vm_area_struct *vma)
{

— 5094,5100 —-
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22) || defined(RHEL3)
static int spca5xx_mmap(struct file *file, struct vm_area_struct *vma)
{

***************
*** 5144,5150 ****
return 0;
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION (2,4,22)
static struct file_operations spca5xx_fops = {
.owner = THIS_MODULE,
.open = spca5xx_open,
— 5149,5155 —-
return 0;
}

! #if LINUX_VERSION_CODE >= KERNEL_VERSION (2,4,22) || defined(RHEL3)
static struct file_operations spca5xx_fops = {
.owner = THIS_MODULE,
.open = spca5xx_open,
***************
*** 8458,8464 ****

}

! #if LINUX_VERSION_CODE > KERNEL_VERSION(2,4,22)
static struct usb_driver spca5xx_driver = {
#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,16)
.owner = THIS_MODULE,
--- 8463,8469 ----

}

! #if LINUX_VERSION_CODE > KERNEL_VERSION(2,4,22) || defined(RHEL3)
static struct usb_driver spca5xx_driver = {
#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,16)
.owner = THIS_MODULE,
***************
*** 8470,8476 ****
};
#else
static struct usb_driver spca5xx_driver = {
! #if LINUX_VERSION_CODE > KERNEL_VERSION(2,4,20)
THIS_MODULE,
#endif
“spca5xx”,
— 8475,8481 —-
};
#else
static struct usb_driver spca5xx_driver = {
! #if LINUX_VERSION_CODE > KERNEL_VERSION(2,4,23)||defined(RHEL3)
THIS_MODULE,
#endif
“spca5xx”,
Only in spca5xx-20060402-wu/drivers/usb: spca5xx.c~
diff -rc spca5xx-20060402/Makefile spca5xx-20060402-wu/Makefile
*** spca5xx-20060402/Makefile2006-04-03 04:27:03.000000000 +0800
— spca5xx-20060402-wu/Makefile2006-04-10 18:14:27.000000000 +0800
***************
*** 32,37 ****
— 32,38 —-
# Setup defines
DEFINES   += -DCONFIG_USB_SPCA5XX_MODULE=1 -DMODULE -D__KERNEL__
DEFINES   += -DVID_HARDWARE_SPCA5XX=0xFF -DSPCA5XX_VERSION=”$(VERSION)”
+ DEFINES   += -DRHEL3

ifneq ($(shell uname -r | cut -d. -f1,2), 2.4)

Only in spca5xx-20060402-wu: Makefile~
----------------------------------
没有用过CDMA,只用过实验箱上的GPRS模块,插上动感地带的手机号码卡,pppd拨号。
拨上了之后除了慢、贵、不稳定和网络不好时会掉线以外,用tcp/ip协议传输消息、文件,与普通的以太网没区别。
感觉GPRS网用UDP协议发短一些的消息,还行,但有时还是会丢。
发文件或图像一定得用TCP协议,虽然慢了一点,但毕竟TCP有出错重传的机制。

网上的说法是:实际速度CDMA在150K左右,而GPRS在45K左右,CDMA是GPRS速度的三倍多。

但实验箱上GPRS模块实际就是一个接在串口的调制解调器,GPRS模块与串口通讯的速度为115200bps
8比特/秒bps(bits per second)= 1字节/秒Bps(bytes per second)
1024 Bps = 1 KBps
115200bps/8/1024=14KB/s,虽然网上说的理论上的GPRS访问速度很高,但受限于串口的速度,实际速度都在10KB/s以下。

分辨率240*240,quality为50的jpeg图片大小约4KB,以1KB为单位发送的话

TCP发送的过程:
A发送端:我要传了(等接收端回应要延迟)
B接收端:传吧
A发送端:传1KB的数据(传送也要延迟)
A发送端:收到了么?(确认还要延迟)
B接收端:我收到了

发1帧图像4KB就要4次这样的过程,还没算上出错重传。再加上,10KB/s说的只是下行速度,不知道上行速度怎么样。
如此小的分辨率和如此低的图像质量,发送1帧图像要1秒吧?
大点的分辨率高点的质量,那就是:惨、惨、惨、惨不忍睹!

除非课题要求一定要用GPRS,不然我发图像和文件肯定选择用以太网。
===================================================================
综上所述:CDMA没用过,但再怎么说都比GPRS好点吧。

你可能感兴趣的:(linux,摄像头,交叉编译,SEED-DIM3517)