if (Usage1!=0) {
UsageLength++;
if (Usage2!=0) {
UsageLength++;
if (Usage3!=0) {
UsageLength++;
}
}
}
// Convert usages into an output report
NTSTATUS status = HidP_SetButtons(HidP_Output, HID_USAGE_PAGE_LED, 0, UsageList, &UsageLength, HidPreparsedData, OutputReport, OutputReportLen);
if (status!=HIDP_STATUS_SUCCESS) {
delete OutputReport;
return;
}
printf(' Output report: ');
for (ULONG i=1; i<OutputReportLen; i++) printf(' %02X', OutputReport[i]);
printf('
');
// Send off output report
DWORD TxdBytes;
if (!WriteFile(hHidKbd, OutputReport, OutputReportLen, &TxdBytes, NULL))
printf('XXX Could not write value %d
', GetLastError());
else if (TxdBytes==OutputReportLen) printf(' Wrote output report 0K
');
else printf('XXX Wrong number of bytes written: %d
',TxdBytes);
delete OutputReport;
}
User mode HID clients can send and receive HID
The functions
If you have a HID keyboard, you can run
There is only one HID device in the system. It is opened and
Test 2 reads any input reports from the HID keyboard. In this example, I pressed Ctrl+Alt+Del followed by A, B, C, and Esc. You can see how an input report is produced every time a key is pressed or released. The actual input report is in exactly the same format as the raw USB interrupt transfer shown in Table 21.9.
If you remember from Chapter 21, the USB example driver, UsbKbd, kept on receiving input interrupt data even if no state changes had occurred. The HID class driver sensibly filters out these redundant input reports and only returns data when a key is pressed or released.
Test 3 sends several output reports to flash the LEDs on the keyboard.
Listing 23.6 Example
Test 1
Symbolic link is \. 00000000000000b#{4d1e55b2-f16f-11cf-88cb-001111000030}
Found HID device
HID attributes: VendorID=046A, ProductID=0001, VersionNumber=0305
Top level Usage page 1 usage 6
Found HID keyboard
InputReportByteLength 9
OutputReportByteLength 2
FeatureReportByteLength 0
NumberLinkCollectionNodes 1
NumberInputButtonCaps 2
NumberInputValueCaps 0
NumberOutputButtonCaps 1
NumberOutputValueCaps 0
NumberFeatureButtonCaps 0
NumberFeatureValueCaps 0
Input button capabilities
ButtonCaps[0].UsagePage 7
.Usages 224..231
ButtonCaps[1].UsagePage 7
.Usages 0..101
Output button capabilities
ButtonCaps[0].UsagePage 8
.Usages 1..3
Opened OK
Test 2
Input report 0: 01 00 00 00 00 00 00 00 Left Ctrl pressed
Usages set: 07:E0 (Break: ) (Make: E0)
Input report 0: 05 00 00 00 00 00 00 00 Left Alt pressed
Usages set: 07:E0 07:E2 (Break: ) (Make: E2)
Input report 0: 05 00 63 00 00 00 00 00 Del pressed
Usages set: 07:E0 07:E2 07:63 (Break: ) (Make: 63)
Input report 0: 05 00 00 00 00 00 00 00 Del released
Usages set: 07:E0 07:E2 (Break: 63) (Make: )
Input report 0: 00 00 00 00 00 00 00 00 Left Ctrl & Alt released
Usages set: (Break: E0 E2) (Make: )
Input report 0: 00 00 04 00 00 00 00 00 A pressed
Usages set: 07:04 (Break: ) (Make: 04)