Giter Site home page Giter Site logo

Android 13 issue. about uvccamera HOT 6 OPEN

onemetafox avatar onemetafox commented on July 16, 2024
Android 13 issue.

from uvccamera.

Comments (6)

Nalethen avatar Nalethen commented on July 16, 2024 5

I have had this problem also and did some investigation into it. It seems that it is not caused by Android 13 since in some phones with it, like Samsung S21, it works. The phones I tested which didn’t work were Samsung A12, A13 and A33. I’m also pretty sure it happened on some of these back when they still had Android 12. Also one USB camera worked if I selected the lowest resolution it had (160x120) but anything higher and it didn’t work.

I managed to get it working by editing libuvc_internal.h and modifying LIBUVC_NUM_TRANSFER_BUFS 10 to be smaller. 7 was the highest where it still worked for me so I left it at 5.

This seems like just a workaround though and that the root problem is somewhere else. The problem seemed to be that frame buffers in libuvc were getting corrupted, possibly because the transfer buffers were getting overwritten or cleared before the data had been fully processed by the consuming side. When requesting mjpeg this results in decoding error and no frames will be produced, but when requesting YUV the corrupted frames will be shown on the preview. It looks to me like some concurrency or timing issue, but I don’t have much experience with C language or USB protocols so trying to debug the problem has been pretty challenging. For now I will just go with lowering the LIBUVC_NUM_TRANSFER_BUFS and if no problems come up leave it at that.

from uvccamera.

BekhruzDev avatar BekhruzDev commented on July 16, 2024

Yes, i am having a similiar issue too

from uvccamera.

oleszczyk avatar oleszczyk commented on July 16, 2024

I have exactly the same issue. 2 devices:

  • Xiaomi MI A2 lite - Androird 9, SDK 28
  • Lenovo Tab M8 - Androird 9, SDK 28.

For Xiaomi everything works as it should. But on Lenovo there was no MJPEG frames generation at all - preview black, no onFrame callback calls etc.
Switching from FRAME_FORMAT_MJPEG to FRAME_FORMAT_YUYV resulted with malformed frames: part of an image was distorted with green lines, and single wide green stripe on the image bottom.

I have tested solution proposed by @Nalethen and it worked! I have decreased LIBUVC_NUM_TRANSFER_BUFS to 5 and it looks like right now MJPEG frames are correctly generated.

If you have any "better" solution that this workaround I would really appreciate it.

from uvccamera.

guitarooman14 avatar guitarooman14 commented on July 16, 2024

I have had this problem also and did some investigation into it. It seems that it is not caused by Android 13 since in some phones with it, like Samsung S21, it works. The phones I tested which didn’t work were Samsung A12, A13 and A33. I’m also pretty sure it happened on some of these back when they still had Android 12. Also one USB camera worked if I selected the lowest resolution it had (160x120) but anything higher and it didn’t work.

I managed to get it working by editing libuvc_internal.h and modifying LIBUVC_NUM_TRANSFER_BUFS 10 to be smaller. 7 was the highest where it still worked for me so I left it at 5.

This seems like just a workaround though and that the root problem is somewhere else. The problem seemed to be that frame buffers in libuvc were getting corrupted, possibly because the transfer buffers were getting overwritten or cleared before the data had been fully processed by the consuming side. When requesting mjpeg this results in decoding error and no frames will be produced, but when requesting YUV the corrupted frames will be shown on the preview. It looks to me like some concurrency or timing issue, but I don’t have much experience with C language or USB protocols so trying to debug the problem has been pretty challenging. For now I will just go with lowering the LIBUVC_NUM_TRANSFER_BUFS and if no problems come up leave it at that.

You made my day. One week on this issue and finally found your solution. Thanks a lot.

from uvccamera.

buenocorp avatar buenocorp commented on July 16, 2024

It didn't work for me. Could you share an example that works with these changes?

from uvccamera.

suyeongpark avatar suyeongpark commented on July 16, 2024

After debugging on multiple devices, it appears that the problem lies within the submit_bulk_transfer() function in the libusb/libusb/os/android_usbfs.c file, where multiple ioctl() calls are made. The function operates correctly when num_urbs is 1, but does not function properly when there are multiple URBs.

This seems to be code intended to reduce the buffer size instead of making multiple calls, likely aimed at devices with lower performance. However, simultaneous calls might actually saturate the processing capacity of the host controller on lower performance devices, leading to issues.

While converting this part to asynchronous code could solve the problem, it would require extensive modifications. Instead, forcing num_urbs to 1 by setting bulk_buffer_len = transfer->length within the submit_bulk_transfer() function allows data to be fetched, although this might reduce the quality of the USB camera video depending on the device's performance.

// Code that was commented out:
// if (dpriv->caps & USBFS_CAP_BULK_SCATTER_GATHER) {
// /* Good! Just submit everything in one go /
// bulk_buffer_len = transfer->length ? transfer->length : 1;
// use_bulk_continuation = 0;
// } else if (dpriv->caps & USBFS_CAP_BULK_CONTINUATION) {
// / Split the transfers and use bulk-continuation to
// avoid issues with short-transfers /
// bulk_buffer_len = MAX_BULK_BUFFER_LENGTH;
// use_bulk_continuation = 1;
// } else if (dpriv->caps & USBFS_CAP_NO_PACKET_SIZE_LIM) {
// / Don't split, assume the kernel can alloc the buffer
// (otherwise the submit will fail with -ENOMEM) /
// bulk_buffer_len = transfer->length ? transfer->length : 1;
// use_bulk_continuation = 0;
// } else {
// / Bad, splitting without bulk-continuation, short transfers
// which end before the last urb will not work reliable! /
// / Note we don't warn here as this is "normal" on kernels <
// 2.6.32 and not a problem for most applications */
// bulk_buffer_len = MAX_BULK_BUFFER_LENGTH;
// use_bulk_continuation = 0;
// }

// Added code. Set bulk_buffer_len to transfer->length to ensure num_urbs is 1
bulk_buffer_len = transfer->length;
use_bulk_continuation = 0;

from uvccamera.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.