第一次开启uvc摄像头预览正常,但是一拍照就会退出app。
再次尝试打开摄像头都会报下面的这种错误。
尝试在代码里搜reprocessFrame处理的函数,但是没有找到。
出错的部分logcat如下:
E/CameraHal( 185): getFrame(614): getFrame(614): VIDIOC_DQBUF Failed!!! err[I/O error]
E/CameraHal( 185): getFrame(620): getFrame(620): camera driver or device may be error, so notify CAMERA_MSG_ERROR
E/Camera ( 1696): Error 100
E/CAM_CameraActivity( 1696): Camera error callback. error=100
E/CAM_Util( 1696): Show fatal error dialog
部分dmesg如下:
7>[ 40.997691] urb is deactive, this urb complete cancel!
<7>[ 40.998039] urb is deactive, this urb complete cancel!urb is deactive, this urb complete cancel!
<7>[ 41.023370] urb is deactive, this urb complete cancel!urb is deactive, this urb complete cancel!
<6>[ 41.813237] vcodec_service: ff9a0000.vpu_service: power off...<6>[ 41.813272] vcodec_service: done
<7>[ 47.452804] urb is deactive, this urb complete cancel!
<7>[ 47.453055] urb is deactive, this urb complete cancel!urb is deactive, this urb complete cancel!
<7>[ 47.476799] urb is deactive, this urb complete cancel!pcd_pullup, is_on 0
原因:
kernel uvc driver内的uvc_video_complete_fun函数在检查urb_state时发现state为UrbDeactive,直接报错返回了
if (atomic_read(urb_state)==UrbDeactive) {
printk(KERN_DEBUG "urb is deactive, this urb complete cancel!");
uvc_queue_cancel(queue, urb->status == -ESHUTDOWN);
return;
}
造成deactive的原因是,上一次打开设备后调用了uvc_video_suspend函数,其中又调用了uvc_uninit_video函数将urb全部deactive了。在第二次打开uvc设备时调用的uvc_video_resume函数中又调用了uvc_init_video_bulk进行uvc_stream的重新初始化,但是没有对Urb重新active。导致第二次进入预览界面会造成urb数据获取不到的问题。
分析过程:
一开始追到hal层,发现每次get frame都会失败,而且总是报mjpeg data error。由于处理mjpeg frame的code没有开放,无法继续查下去。
为了排除hal层decode frame引起bug的嫌疑。从网上找了直接通过V4L2打开video设备的apk再次尝试。最后发现还是会报错。确认是driver的问题。打开uvc的全部log,最后发现第二次进入preview状态时总是报Urb Deactive的error。最后通过log,找到对应的suspend和resume使用的函数,将ACTIVE的流程添加进去。问题解决。
参考文章:
http://dev.t-firefly.com/thread-5069-1-1.html
我的修改补丁patch见: