zoukankan      html  css  js  c++  java
  • kinect 无法在我的android开发板上显示的分析

    之前在网上发现黑客已经将kinect移植到android上,使用的beagleboard平台。公司想在kinect上深耕一下,所以需要将kinect在公司的android开发板上实现。记录以备忘。

    一,按照黑客的教程,将之移植到beagleboard C4平台上。挺顺利。但深度图像只能维持几秒钟,因beagleboard不是我的最终目的,此问题搁置,beagleboard作为参考。黑客的教程如下:

    http://www.noritsuna.com/archives/2011/01/openframeworks_kinect_android.html

    顺便说一下,配置开发工具很麻烦,尤其是有些需要FQ出去下,所以建议下载上面网页结尾处作者提供的完整软件包。解压后修改一下环境变量即可用。可以更懒一下:新建一个跟作者相同的用户名,将包解压到相应的文件夹,整个工程及其软件就可以用了。

    二、将之移植到自己的android开发板。硬件平台就不具体说了,不是国际大厂的。

    出错:加速度计显示正常,但深度图像没有显示,全黑。

    到此为止,我一直没有仔细看代码。呵呵。没办法了,看代码吧。

    框架:openframework

    流程:openframework->ofxAndroid->ofxKinect->freenect->libusb之后就是linux内核?

    前面不说了,可以借助打印log进行分析。没有显示的原因是ofxKinect::threadedFunction()函数中,

      


    最后一条语句设置回调函数,具体实现如下
    将回调函数赋值给dev->depth-cb, 之后调用freenect_start_depth(kinectDevice);
    函数fnusb_start_iso()将参数depth_process设为回调函数,
     
    //在此函数中将iso_callback函数设为回调函数
     
    而iso_callback函数又会调用strm->cb,depth_process。
     
    depth_process中会执行dev->depth-cb。
    调来调去的真的很麻烦。
    至此,整个流程结束。那回调函数会在何时调用?也就是libusb_fill_iso_transfer函数中的  transfer->callback会在哪里被调用执行?
    在ofxKinect用cscope搜一下callback,只有usbi_handle_transfer_completion回调用到transfer->callback,那usbi_handle_transfer_completion会在哪里被调用?再搜
    有八九条,我们只关注标志为 LIBUSB_TRANSFER_COMPLETED的,只有一条,handle_iso_completion函数。搜handle_iso_completion
    reap_for_handle   ---  op_handle_events  ,此函数被设置在const struct usbi_os_backend linux_usbfs_backend 结构体中,赋值语句:
    .handle_events = op_handle_events,
     
    看看linux_usbfs_backend 是不是引用,还有.handle_events在哪里被调用?
    在libs/libusb/core.c中
     
    在libs/libusb/io.c中函数handle_events(){   usbi_backend->handle_events}
    io.c中有两处调用到handle_events()函数
    4 io.c          libusb_handle_events_timeout 1946 r = handle_events(ctx, &poll_timeout);
    5 io.c          libusb_handle_events_locked  2022 return handle_events(ctx, &poll_timeout);
    正确的调用应该是第二个,libusb_handle_events_locked,
    搜libusb_handle_events_locked,除了函数定义只有一处头文件的声明。看起来上面分析不对,那是libusb_handle_events_timeout是正确调用?
    libusb_handle_events_timeout被
     
    调用,
    搜libusb_handle_events,排除被bulk及control接口调用,只有在libusb10.c的两处
    1 usb_libusb10.c fnusb_process_events      66 return libusb_handle_events(ctx->ctx);
    2 usb_libusb10.c fnusb_stop_iso           245 libusb_handle_events(ctx->usb.ctx);
    2是usb停止时的调用,1应为我们的目标,
     
    看到fn了,呵呵,我们的路应该是正确的。
     
    搜freenect_process_events,libs/libfreenect/libfreenect.hpp中
     
         // Do not call directly, thread runs here
    呵呵,终于到头了。
    整个流程就是这样,但对无法显示的问题还是无解。需要log。
    先这样,将libusb的log打印出来再说。没有log就像瞎子一样。

    4.15日编辑
    今天把libusb的log输出出来了,写下以备忘。
    libusb的log部分实在libusb.h中定义的
    最终所有的log输出都定位到usb_ofLog(level, fmt)函数,在core.c中
    libusb的日志输出是标准的输入输出。有个方案,可以在上面的函数中将日志保存到一个文件中。我用的是另一条路:
    采用android的日志模式
    1、修改libusb.h,修改成这样
     
    主要是上面的enum,将第一个赋值为3,另外将几个宏定义重定位到另一个函数usb_ofLog,这个函数需要我们自己改。
    在core.c 最后添加如下:
     
    见android的日志规则引用进来。之后重编译,就可以看到可爱的日志啦。

    4.26日更新

    已经在自己的开发板上跑起来了。有图像输出,但只是二值图,这个应该是上层画图的时候的问题。先记录一下解决的过程。

    libusb日志打印成功后,分析得知libusb得到的数据为全0,libusb的底层支持是usbfs,所以跟踪到kernel的usbfs部分,usb/core/devio.c中,有函数processcompl(),

    将语句

    if (as->userbuffer && urb->actual_length) {

    修改成 
    if(as->userbuffer){
    之后图像能够正常输出,跟板子的提供商联系,urb->actual_length在usb core中没有被赋值。bug
    他提供的解决方案,
    在driver/xxx/usb/dwc_otg/dwc_otg_hcd_intr.c中
    if (++_qtd->isoc_frame_index == urb->number_of_packets) {前加下面的语句
    urb->actual_length += frame_desc->actual_length;
    最后的结果是:
    default:
    DWC_ERROR("%s: Unhandled _halt_status (%d)/n", __func__,
     _halt_status);
    BUG();
    break;
    }
    urb->actual_length += frame_desc->actual_length;
    if (++_qtd->isoc_frame_index == urb->number_of_packets) {

    如果只是按照他提供的方案改,帧率很低,原因待分析。

  • 相关阅读:
    Spring Boot 7:配置文件信息读取
    Spring Boot 6:自定义filter
    Spring AOP:Java动态代理和CGlib
    Spring AOP:概念
    设计模式(二)---策略模式
    设计模式(一)--装饰模式
    java并发编程实战笔记
    剑指offer java -查找旋转数组的最小数字
    读书计划
    协议初学
  • 原文地址:https://www.cnblogs.com/leino11121/p/2381919.html
Copyright © 2011-2022 走看看