How to properly unblock libusb_bulk_transfer
标题的名字来自于libusb开发社区How to properly unblock libusb_bulk_transfer,根据作者的描述,我也有相同的需求。我觉得这个题目特别好,尽管这个问题我还没有完全解决,决定也以这个名字为题写一篇记录。
需要使用libusb_bulk_transfer进行数据的传输,且最后一个timeout参数设置为0来实现BLOCK的传输,但是在传输过程中如果是超长时间的BLOCK,我想中断怎么办?也不必说是超长BLOCK,就是BLOCK了用户有权利中断传输如何实现?这个是完全可以有的需求,也是已经普遍存在的需求,对于使用libusb来进行的传输如何实现呢?这个问题困惑了我好久了。
方法1:
该文章的最后解决方法是timeout参数设置一个比较大的值10S或者更长,然后再来判断错误代码是不是TIMEOUT了;这种方法我并不乐于接受,我像要的是用户不中止,那我就一直BLOCK在这里,那这个TIMEOUT应该如何设置,设置成一年?;)方法2:
那到底还有没有一个可以中断BLOCK的方法,现在回到libusb开发者网站对libusb_bulk_transfer的描述:
The main advantage of this model is simplicity: you did everything
with a single simple function call.However, this interface has its limitations. Your application will
sleep inside libusb_bulk_transfer() until the transaction has
completed. If it takes the user 3 hours to press the button, your
application will be sleeping for that long. Execution will be tied up
inside the library - the entire thread will be useless for that
duration.Another issue is that by tieing up the thread with that single
transaction there is no possibility of performing I/O with multiple
endpoints and/or multiple devices simultaneously, unless you resort to
creating one thread per transaction.Additionally, there is no opportunity to cancel the transfer after the request has been submitted.
来源:Lisbusb api-1.0 io:The synchronous interface。
最后一句话真够狠的,直接把这条路封死了:如果BLOCK了,你是没有办法UNBLOCK(cancel)的。封死这条路后,他开始推荐使用异步通信来代替没有办法中断的同步通信,我暂时没有办法接受这个建议。同步通信Google的Adb也在用,为什么就得要我换呢?
方法3:
这个是我自己试的,也是在网上搜索出来了,lisbusb你不提供中断传输的API,那么我就从根上断了你。我来操控线程,直接把你所在的线程给kill掉,kill有两种方法:1.pthread_kill这个函数,不过在Bionic中并没有实现这个函数。2.使用传统的信号机制,但是我的实验结果是会将整个调用进程给kill掉,有点过头了,目前还不知道根据原因在哪里。方法4:
还有几个idea没有进行测试,如:关闭libusb_device_handle,让其传输不成;使用libusb_reset_device。