[fpc-pascal] USB Human Interface Devices

Stefan V. Pantazi svpantazi at gmail.com
Wed Aug 21 23:30:31 CEST 2019


 From your example it looks like you placed the device reading 
(interrupt read) and writing (set report) into the same read thread. I 
thought  keeping them separate was a good idea: tight loop reads and 
less frequent writes (LCD updates).

Libusb is supposed to be thread-safe. Not really an issue for your app 
but if you need to make sure only one thread out of multiple threads is 
processing libusb events the library has asynchronous API that does 
offer locking functionality.

On 8/21/19 3:48 PM, James Richters wrote:
> Well..  It doesn’t always work just reading constantly and writing in a different thread..
> 
> So I have my fast read loop always reading then my LCD write loop sending the 3 packets every 0.3 Seconds.. and it functions ok, and I don’t miss too many counts... but every so often I get this message:
> libusb: warning [handle_timeout] async cancel failed -5 errno=0
> 
> I have a timeout on my read loop of 10ms.  I tried setting that to 0 so it would just wait for input in it's thread.. but when I do that I get this as soon as I attempt to write to it:
> An unhandled exception occurred at $00007FFF189F03C6:
> EAccessViolation: Access violation
>    $00007FFF189F03C6
>    $00007FFF189EDA21
>    $00007FFF17AAA1A1
>    $00007FFF17AA9CB5
>    $000000006B607FFB
>    $000000006B6081E7
>    $000000006B60C695
>    $000000006B605D6F
>    $000000006B607E40
>    $000000010001B1CA
>    $00000001000021BF  main,  line 445 of whb04b-4_test.pas
>    $00000001000022B6
>    $000000010000EC20
>    $0000000100001880
>    $00007FFF17B47E94
>    $00007FFF18A4A251
> 
> Also if I put in a really long timeout like 1000ms I get that.  Line 445 is
> libusbhid_set_report(device_context, HID_REPORT_TYPE_FEATURE, $6 , 8 , WhB04_Packet1 );
> 
> so I can't write while I'm reading or waiting for a read after all.
> 
> So I came up with a scheme to set all the variables in the slow loop then set a Boolean variable when it's done.. then the fast loop checks for the flag if it is idle for a time, meaning it's not trying to keep up with input.. and that does work.. and I don't miss many counts... but it does miss a few... but I STILL get this
> libusb: warning [handle_timeout] async cancel failed -5 errno=0
> 
> even though as far as I can tell, I can't possible be reading and writing at the same time.
> 
> I've updated my test project here: https://github.com/Zaaphod/libusbxhid/blob/master/WHB04B-4_test.pas
> 
> I don't really know what libusb: warning [handle_timeout] async cancel failed -5 errno=0 is trying to tell me... it is having an issue canceling waiting for data after the time out I guess.. but why is that a problem?
> 
> Any Ideas?
> 
> James
> 
> -----Original Message-----
> From: fpc-pascal <fpc-pascal-bounces at lists.freepascal.org> On Behalf Of James Richters
> Sent: Wednesday, August 21, 2019 8:30 AM
> To: 'FPC-Pascal users discussions' <fpc-pascal at lists.freepascal.org>
> Subject: Re: [fpc-pascal] USB Human Interface Devices
> 
> I FINALLY wrote some data to the LCD!!   YAY !!!   I was trying to get the python application to work.. without any luck.. but I ended up going ahead and trying Zadig changing the driver to libusb-win32...  After I gave up on Python, I went back to FPC and just ran my existing sample program, and I noticed where it used have an error sending to device, it now said 8 bytes sent!!  It's very strange I could read it just fine but not write to it without messing with the driver... but it's working now!
> 
> I tried suspending the read thread to write to it.. and well it must have ended up suspending in the middle of a read because the whole thing locked up.. so I just tried as suggested and let it keep reading in a tight loop in it's own thread and then just throw in a write every few seconds on the main program.. and that actually worked fine.. I guess libusb takes care of worry about finishing a read before writing.. I think I did see libusb had something to do with threads.
> 
> So now it's just a matter of small details.     The display is a little odd... in that instead of sending it just a real number, you send it an integer for the numbers before the decimal and another integer for the numbers after the decimal.. but it's 2 bytes for each (4 bytes total)  but they are in reverse order.. I need to send LowByte_Integer, High_Byte_Integer, LowByte_decimal, High_Byte_decimal  so the bits from a 16 bit integer end up being 76543210,FEDCBA98  I think this is that edian byte order thing that was mentioned.  I'm just curious if there is already a function available to reverse these like this.. or if I just need to write my own.  It's just some rotates and then split it, so I can do that, but I'm just wondering if there is something already there to do this.. I seem to recall that this kind of thing needs to happen quite a bit.
> 
> Also I need to stick a $06 in front of all my packets to send to the device.  I have my data all in arrays,  so I want to do something like this Device_Array[0]:=$06; Device_Array[1..7] := LCD_Array[0..6] ;
> 
> Ah.. but that doesn't work.. is there a way to do this with syntax or do I just need to make a loop to copy the array elements the way they need to be?
> 
> James
> _______________________________________________
> fpc-pascal maillist  -  fpc-pascal at lists.freepascal.org https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
> _______________________________________________
> fpc-pascal maillist  -  fpc-pascal at lists.freepascal.org
> https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal
> 

-- 
_______________________________________________________


More information about the fpc-pascal mailing list