USB HID Host Driver for Windows


What is AHid.dll?


AHid.dll is an easy-to-use USB HID Host Driver API for Windows. You can use it with C++, LabVIEW or any other programming language that supports the common DLL approach. Its straight forward concept with read(), write() and find() functions allows you to develop USB HID applications in minutes.

So, stop wracking your brain and start USB HID development using AHid.dll!



Features


AHid.dll supports 32 and 64 bit Windows Operating Systems.

AHid.dll can separate the functions of your USB Composite Device into several data pipes for individual access. And it can detect your HID devices automatically.

AHid.dll supports plug and play, so you can connect or remove your USB device without data loss. It also uses asynchronous data transfer. This will avoid freezing your application while waiting for a data transfer to finish.

AHid.dll can connect to Input and Output pipes concurrently. It can send and receive Reports with standard ID (zero) and any other ID as well.

You can use AHid.dll with Low- and Full-Speed USB devices. There is no additional driver required (in contrast to CDC and virtual COM Port).

Private individuals can use AHid.dll for free. Download a sample project and start your development.



Interface


AHid.dll requires only five functions to read, write or find your HID device on USB:

  • AHid_init(): this function initializes the driver and has to be called first
  • AHid_register(): register a data pipe of your HID device for data transfers
  • AHid_read(): read from the device
  • AHid_write(): write to the device
  • AHid_find(): check if the device is attached or removed

Take a look at the AHid.h header file for further informations.


Download


The sample projects work out of the box, are self-explaining and a good starting point for your development. If you have any questions, just drop us a line.


Sample projects:




Workflow


The workflow can be devided into five parts: configuration of your HID device, driver initialization,the writer function, the reader function and tracking the connection state.


Configuration of your HID device

Here, we use the following values in the Device Descriptor: VID = 0xAADE, PID = 0xFFFF.

The Report Descriptor is configured to use two endpoints for Input and Output transfers with a data size of 8 bytes each and no Report ID.

unsigned char report_descriptor[ 28 ] =
{
0x06, 0xFF, 0xFF, // USAGE PAGE ( verndor defined )
0x09, 0x00, // USAGE ( undefined )
0xA1, 0xFF, // COLLECTION ( vendor defined )

0x09, 0x00, // USAGE ( undefined )
0x15, 0x00, // LOGICAL MINIMUM ( 0 )
0x26, 0xFF, 0x00 // LOGICAL MAXIMUM ( 255 )
0x95, 0x08, // REPORT COUNT ( 8 )
0x75, 0x08, // REPORT SIZE ( 8 )
0x91, 0x02, // OUTPUT ( data, var, abs )

0x09, 0x00, // USAGE ( undefined )
0x95, 0x08, // REPORT COUNT ( 8 )
0x75, 0x08, // REPORT SIZE ( 8 )
0x81, 0x02, // INPUT ( data, var, abs )

0xC0, // END COLLECTION
};

With this HID device configuration, you can use AHid.dll as it is shown below.


Initialization

The very first step is to initialize the driver and to setup the communication pipes for data transfers.

// Note: all definitions starting with AHID_ are defined in AHid.h header file

if ( AHid_init() == AHID_OK )
{
AHid_register( &OutPipe, 0xAADE, 0xFFFF, -1, 0, 8, AHID_REPORT_TYPE_OUTPUT );
AHid_register( &InPipe, 0xAADE, 0xFFFF, -1, 0, 8, AHID_REPORT_TYPE_INPUT );
}
else
{
// handle error here
}

The AHid_register() function returns a pipe handle (OutPipe/InPipe) that is used in all AHid function calls as a reference.

The values for VID and PID are defined in the USB Descriptor of your HID device. You can find these values in the Windows Hardware Manager as well.

The interface ID is not used here and therefore set to -1 (this is quite common). But if your device has multiple interfaces (like a Composite Device), just set it to the desired interface number.

The Report ID is 0, the Report Size is 8 and in case of a transfer direction from Host to device, the Report Type is set to OUTPUT.

All these parameters are device specific and it is absolutely fundamental to use the proper values. They can be found in the related Device, Interface and Report Descriptors of your HID device.

If your device is not working with AHid.dll and you are unsure to have the correct parameters, you can try one of the USB Analyzer sofware available on the internet. Use any free or trial version you can find, make a snapshot of the USB Device Enumeration Process and send the results to us for help.


Writer Function

The Writer Function handles data transfers from Host to device.

if ( AHid_write( OutPipe, Buffer, 8, &BytesWritten ) != AHID_OK )
{
// handle error here
}

OutPipe is the handle returned by the corresponding AHid_register() function.

The Buffer holds the data to transfer. In this case, it is a byte array of 8 bytes.

The number of bytes to send is also 8. This value must always be equal to (or a multiple of) the Report Size parameter of the corresponding AHid_register() function. So, only full Reports are send by AHid.dll.

The value of BytesWritten is set by AHid.dll. If no error occurs, it should be equal to the number of bytes to send (here 8).


Reader Function

The Reader Function handles data transfers from HID device to Host.

if ( AHid_read( InPipe, Buffer, 8, &BytesRead ) == AHID_OK )
{
// handle data here
}

InPipe is the handle returned by the corresponding AHid_register() function.

The Buffer variable holds the data send from your HID device. Here, it is a byte array of 8 bytes.

The Buffer size is set to 8 bytes too. This value must always be equal to (or a multiple of) the Report Size parameter of the corresponding AHid_register() function. So, only full Reports are received by AHid.dll.

The value of BytesRead is set by AHid.dll and is always equal to (or a multiple of) the Buffer size or zero in case that no data was received.

The Reader Function should be implemented inside a Timer Callback. Assuming that a Full Speed USB device can send a Report every millisecond, there can be at most 64 * 1000 bytes transferred. So, according to that assuption, you can increase the Buffer and its size to a thousand times of your Report Size ( here 8 ) and set the Timer Callback to fire only once a second ( 1000 ms ).
But any other interval and buffer size is possible as long as it is a multiple of the Report Size set in AHid_register().

And don't be afraid to miss some data - AHid.dll will buffer it meanwhile.


Connection State

The Connection State should be tracked inside a Timer Callback.

if ( AHid_find( OutPipe ) == AHID_OK )
{
// show message 'CONNECTED'
}
else
{
// show message 'DISCONNECTED'
}

OutPipe is the handle of the corresponding pipe.

The AHid_find() function is not time critical. If your HID device is removed from USB long time ago, the application will not crash. So, you can securely use an intervall of one second or even ten seconds if you like.