reanchear
驱动小牛
驱动小牛
  • 注册日期2004-06-17
  • 最后登录2016-01-09
  • 粉丝0
  • 关注0
  • 积分40分
  • 威望253点
  • 贡献值0点
  • 好评度102点
  • 原创分0分
  • 专家分0分
阅读:3391回复:4

基于linux2.6.23核,usb camera 驱动开发同仁们请进

楼主#
更多 发布于:2008-02-02 19:52
各路同仁:
    现今我正在进行基于linux2.6.23内核的usb camera 驱动开发。目前主要是在spca5xx-20060402的框架上进行我们自己的camera linux驱动开发。现今遇到了一个比较麻烦的问题如下:

当我在open device,进入到spca50x_init_isoc时,在调用提交urb的时候出现linux系统死机(鼠标,键盘等外围设备没有响应,只能开机重起)。调用代码如下,请大家帮忙看看分析一下,给我点提示吧,谢谢阿!

static int spca50x_init_isoc(struct usb_spca50x *spca50x)
{

    struct urb *urb;
    int fx, err, n;
    int intpipe;
    PDEBUG(3, "*** Initializing capture ***");
/* reset iso context */
    spca50x->compress = compress;
    spca50x->curframe = 0;
    spca50x->cursbuf = 0;
    spca50x->frame[0].seq = -1;
    spca50x->lastFrameRead = -1;

    spca50x_set_packet_size(spca50x, spca50x->pipe_size);
    PDEBUG(2, "setpacketsize %d", spca50x->pipe_size);

    for (n = 0; n < SPCA50X_NUMSBUF; n++)
   {
    #if LINUX_VERSION_CODE > KERNEL_VERSION(2,5,0)
        urb = usb_alloc_urb(FRAMES_PER_DESC, GFP_KERNEL);
    #else
        urb = usb_alloc_urb(FRAMES_PER_DESC);
    #endif
    if (!urb) {
        err("init isoc: usb_alloc_urb ret. NULL");
        return -ENOMEM;
    }
    spca50x->sbuf[n].urb = urb;
    urb->dev = spca50x->dev;
    urb->context = spca50x;
    if (spca50x->bridge == BRIDGE_MyDevice) {
        urb->pipe =
        usb_rcvisocpipe(spca50x->dev, 0x82&0x0f);//2号端点
    } else {
        urb->pipe =
        usb_rcvisocpipe(spca50x->dev, SPCA50X_ENDPOINT_ADDRESS);
    }
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
    urb->transfer_flags = URB_ISO_ASAP;
    urb->interval = 1;
#else
    urb->transfer_flags = USB_ISO_ASAP;
#endif
    urb->transfer_buffer = spca50x->sbuf[n].data;
    urb->complete = spca50x_isoc_irq;
    urb->number_of_packets = FRAMES_PER_DESC;
    urb->transfer_buffer_length =
        spca50x->packet_size * FRAMES_PER_DESC;
    for (fx = 0; fx < FRAMES_PER_DESC; fx++) {
        urb->iso_frame_desc[fx].offset = spca50x->packet_size * fx;
        urb->iso_frame_desc[fx].length = spca50x->packet_size;
    }
    }

#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,41)
    spca50x->sbuf[SPCA50X_NUMSBUF - 1].urb->next = spca50x->sbuf[0].urb;
    for (n = 0; n < SPCA50X_NUMSBUF - 1; n++)
    spca50x->sbuf[n].urb->next = spca50x->sbuf[n + 1].urb;
#endif
    spcaCameraStart(spca50x);
    if (spca50x->bridge == BRIDGE_SONIX) {
    intpipe = usb_rcvintpipe(spca50x->dev, 3);
    usb_clear_halt(spca50x->dev, intpipe);
    }
    PDEBUG(5, "init isoc int %d altsetting %d", spca50x->iface,
       spca50x->alt);
 //在这里提交urb时死机  
 for (n = 0; n < SPCA50X_NUMSBUF; n++)
   {
    spca50x->sbuf[n].urb->dev = spca50x->dev;
#if LINUX_VERSION_CODE > KERNEL_VERSION(2,5,41)
    err = usb_submit_urb(spca50x->sbuf[n].urb, GFP_KERNEL);
#else
    err = usb_submit_urb(spca50x->sbuf[n].urb);
#endif
    if (err) {
        err("init isoc: usb_submit_urb(%d) ret %d", n, err);
        return err;
    }
    }
    for (n = 0; n < SPCA50X_NUMFRAMES; n++) {
    spca50x->frame[n].grabstate = FRAME_UNUSED;
    spca50x->frame[n].scanstate = STATE_SCANNING;
    }

    spca50x->streaming = 1;

    return 0;

}

#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);
#else
static int spca5xx_open(struct video_device *vdev, int flags)
{
#endif
    struct usb_spca50x *spca50x = video_get_drvdata(vdev);

    int err;

#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)
    MOD_INC_USE_COUNT;
#endif
    PDEBUG(2, "opening");

    down(&spca50x->lock);
    /* sanity check disconnect, in use, no memory available */
    err = -ENODEV;
    if (!spca50x->present)
    goto out;
    err = -EBUSY;
    if (spca50x->user)
    goto out;
    err = -ENOMEM;
    if (spca50x_alloc(spca50x))
    goto out;
    /* initialize sensor and decoding */
    err = spca50x_init_source(spca50x);
    if (err != 0) {
    PDEBUG(0, "DEALLOC error on spca50x_init_source\n");
    up(&spca50x->lock);
    spca5xx_dealloc(spca50x);
    goto out2;
    }
    spca5xx_initDecoder(spca50x);
    /* open always start in rgb24 a bug in gqcam
       did not select the palette nor the size  
       v4l spec need that the camera always start on the last setting */
    spca5xx_setFrameDecoder(spca50x);

    spca50x->user++;
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,22)
    file->private_data = vdev;
#endif
    err = spca50x_init_isoc(spca50x);//调用地方
    if (err) {
    PDEBUG(0, " DEALLOC error on init_Isoc\n");
    spca50x->user--;
    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;
    }

    /* Now, let's get brightness from the camera */
    spca50x->brightness = spca50x_get_brightness(spca50x) << 8;
#ifdef SPCA50X_ENABLE_EXPERIMENTAL
    spca50x->nstable = 0;
    spca50x->nunstable = 0;
    spca50x->whiteness = spca50x_get_whiteness(spca50x) << 8;
#else                /* SPCA50X_ENABLE_EXPERIMENTAL */
    spca50x->whiteness = 0;
#endif                /* SPCA50X_ENABLE_EXPERIMENTAL */

  out:
    up(&spca50x->lock);
  out2:
#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)
    if (err)
    MOD_DEC_USE_COUNT;
#endif

    if (err) {
    PDEBUG(2, "Open failed");
    } else {
    PDEBUG(2, "Open done");
    }

    return err;
}

cnwarror
驱动小牛
驱动小牛
  • 注册日期2005-08-20
  • 最后登录2013-07-31
  • 粉丝0
  • 关注0
  • 积分21分
  • 威望257点
  • 贡献值0点
  • 好评度134点
  • 原创分0分
  • 专家分0分
沙发#
发布于:2008-02-11 13:42
现今我正在进行基于linux2.6.23内核的usb camera 驱动开发
cnwarror
驱动小牛
驱动小牛
  • 注册日期2005-08-20
  • 最后登录2013-07-31
  • 粉丝0
  • 关注0
  • 积分21分
  • 威望257点
  • 贡献值0点
  • 好评度134点
  • 原创分0分
  • 专家分0分
板凳#
发布于:2008-02-11 13:46
不懂呀
cnzpwang
驱动牛犊
驱动牛犊
  • 注册日期2007-10-20
  • 最后登录2009-06-04
  • 粉丝0
  • 关注0
  • 积分1分
  • 威望11点
  • 贡献值0点
  • 好评度0点
  • 原创分0分
  • 专家分0分
地板#
发布于:2009-04-16 16:40
sbuf没有初始化
eviliori
驱动牛犊
驱动牛犊
  • 注册日期2008-01-07
  • 最后登录2010-04-14
  • 粉丝0
  • 关注0
  • 积分12分
  • 威望101点
  • 贡献值0点
  • 好评度0点
  • 原创分0分
  • 专家分0分
地下室#
发布于:2010-04-11 00:36
我也正做这个,可以一起交流一下吗?
我的QQ:3745983
游客

返回顶部