Atlas - pp_data_dump.c
Home / ext / SDL / src / hidapi / windows / pp_data_dump Lines: 118 | Size: 14417 bytes [Download] [Show on GitHub] [Search similar files] [Raw] [Raw (proxy)][FILE BEGIN]1#if defined(__MINGW32__) 2 // Needed for %hh 3 #define __USE_MINGW_ANSI_STDIO 1 4#endif 5 6#include <hid.c> 7#include <../windows/hidapi_descriptor_reconstruct.h> 8 9#include <hidapi.h> 10 11void dump_hid_pp_cap(FILE* file, phid_pp_cap pp_cap, unsigned int cap_idx) { 12 fprintf(file, "pp_data->cap[%u]->UsagePage = 0x%04hX\n", cap_idx, pp_cap->UsagePage); 13 fprintf(file, "pp_data->cap[%u]->ReportID = 0x%02hhX\n", cap_idx, pp_cap->ReportID); 14 fprintf(file, "pp_data->cap[%u]->BitPosition = %hhu\n", cap_idx, pp_cap->BitPosition); 15 fprintf(file, "pp_data->cap[%u]->BitSize = %hu\n", cap_idx, pp_cap->ReportSize); 16 fprintf(file, "pp_data->cap[%u]->ReportCount = %hu\n", cap_idx, pp_cap->ReportCount); 17 fprintf(file, "pp_data->cap[%u]->BytePosition = 0x%04hX\n", cap_idx, pp_cap->BytePosition); 18 fprintf(file, "pp_data->cap[%u]->BitCount = %hu\n", cap_idx, pp_cap->BitCount); 19 fprintf(file, "pp_data->cap[%u]->BitField = 0x%02lX\n", cap_idx, pp_cap->BitField); 20 fprintf(file, "pp_data->cap[%u]->NextBytePosition = 0x%04hX\n", cap_idx, pp_cap->NextBytePosition); 21 fprintf(file, "pp_data->cap[%u]->LinkCollection = 0x%04hX\n", cap_idx, pp_cap->LinkCollection); 22 fprintf(file, "pp_data->cap[%u]->LinkUsagePage = 0x%04hX\n", cap_idx, pp_cap->LinkUsagePage); 23 fprintf(file, "pp_data->cap[%u]->LinkUsage = 0x%04hX\n", cap_idx, pp_cap->LinkUsage); 24 25 // 8 Flags in one byte 26 fprintf(file, "pp_data->cap[%u]->IsMultipleItemsForArray = %hhu\n", cap_idx, pp_cap->IsMultipleItemsForArray); 27 fprintf(file, "pp_data->cap[%u]->IsButtonCap = %hhu\n", cap_idx, pp_cap->IsButtonCap); 28 fprintf(file, "pp_data->cap[%u]->IsPadding = %hhu\n", cap_idx, pp_cap->IsPadding); 29 fprintf(file, "pp_data->cap[%u]->IsAbsolute = %hhu\n", cap_idx, pp_cap->IsAbsolute); 30 fprintf(file, "pp_data->cap[%u]->IsRange = %hhu\n", cap_idx, pp_cap->IsRange); 31 fprintf(file, "pp_data->cap[%u]->IsAlias = %hhu\n", cap_idx, pp_cap->IsAlias); 32 fprintf(file, "pp_data->cap[%u]->IsStringRange = %hhu\n", cap_idx, pp_cap->IsStringRange); 33 fprintf(file, "pp_data->cap[%u]->IsDesignatorRange = %hhu\n", cap_idx, pp_cap->IsDesignatorRange); 34 35 fprintf(file, "pp_data->cap[%u]->Reserved1 = 0x%02hhX%02hhX%02hhX\n", cap_idx, pp_cap->Reserved1[0], pp_cap->Reserved1[1], pp_cap->Reserved1[2]); 36 37 for (int token_idx = 0; token_idx < 4; token_idx++) { 38 fprintf(file, "pp_data->cap[%u]->pp_cap->UnknownTokens[%d].Token = 0x%02hhX\n", cap_idx, token_idx, pp_cap->UnknownTokens[token_idx].Token); 39 fprintf(file, "pp_data->cap[%u]->pp_cap->UnknownTokens[%d].Reserved = 0x%02hhX%02hhX%02hhX\n", cap_idx, token_idx, pp_cap->UnknownTokens[token_idx].Reserved[0], pp_cap->UnknownTokens[token_idx].Reserved[1], pp_cap->UnknownTokens[token_idx].Reserved[2]); 40 fprintf(file, "pp_data->cap[%u]->pp_cap->UnknownTokens[%d].BitField = 0x%08lX\n", cap_idx, token_idx, pp_cap->UnknownTokens[token_idx].BitField); 41 } 42 43 if (pp_cap->IsRange) { 44 fprintf(file, "pp_data->cap[%u]->Range.UsageMin = 0x%04hX\n", cap_idx, pp_cap->Range.UsageMin); 45 fprintf(file, "pp_data->cap[%u]->Range.UsageMax = 0x%04hX\n", cap_idx, pp_cap->Range.UsageMax); 46 fprintf(file, "pp_data->cap[%u]->Range.StringMin = %hu\n", cap_idx, pp_cap->Range.StringMin); 47 fprintf(file, "pp_data->cap[%u]->Range.StringMax = %hu\n", cap_idx, pp_cap->Range.StringMax); 48 fprintf(file, "pp_data->cap[%u]->Range.DesignatorMin = %hu\n", cap_idx, pp_cap->Range.DesignatorMin); 49 fprintf(file, "pp_data->cap[%u]->Range.DesignatorMax = %hu\n", cap_idx, pp_cap->Range.DesignatorMax); 50 fprintf(file, "pp_data->cap[%u]->Range.DataIndexMin = %hu\n", cap_idx, pp_cap->Range.DataIndexMin); 51 fprintf(file, "pp_data->cap[%u]->Range.DataIndexMax = %hu\n", cap_idx, pp_cap->Range.DataIndexMax); 52 } 53 else { 54 fprintf(file, "pp_data->cap[%u]->NotRange.Usage = 0x%04hX\n", cap_idx, pp_cap->NotRange.Usage); 55 fprintf(file, "pp_data->cap[%u]->NotRange.Reserved1 = 0x%04hX\n", cap_idx, pp_cap->NotRange.Reserved1); 56 fprintf(file, "pp_data->cap[%u]->NotRange.StringIndex = %hu\n", cap_idx, pp_cap->NotRange.StringIndex); 57 fprintf(file, "pp_data->cap[%u]->NotRange.Reserved2 = %hu\n", cap_idx, pp_cap->NotRange.Reserved2); 58 fprintf(file, "pp_data->cap[%u]->NotRange.DesignatorIndex = %hu\n", cap_idx, pp_cap->NotRange.DesignatorIndex); 59 fprintf(file, "pp_data->cap[%u]->NotRange.Reserved3 = %hu\n", cap_idx, pp_cap->NotRange.Reserved3); 60 fprintf(file, "pp_data->cap[%u]->NotRange.DataIndex = %hu\n", cap_idx, pp_cap->NotRange.DataIndex); 61 fprintf(file, "pp_data->cap[%u]->NotRange.Reserved4 = %hu\n", cap_idx, pp_cap->NotRange.Reserved4); 62 } 63 64 if (pp_cap->IsButtonCap) { 65 fprintf(file, "pp_data->cap[%u]->Button.LogicalMin = %ld\n", cap_idx, pp_cap->Button.LogicalMin); 66 fprintf(file, "pp_data->cap[%u]->Button.LogicalMax = %ld\n", cap_idx, pp_cap->Button.LogicalMax); 67 } 68 else 69 { 70 fprintf(file, "pp_data->cap[%u]->NotButton.HasNull = %hhu\n", cap_idx, pp_cap->NotButton.HasNull); 71 fprintf(file, "pp_data->cap[%u]->NotButton.Reserved4 = 0x%02hhX%02hhX%02hhX\n", cap_idx, pp_cap->NotButton.Reserved4[0], pp_cap->NotButton.Reserved4[1], pp_cap->NotButton.Reserved4[2]); 72 fprintf(file, "pp_data->cap[%u]->NotButton.LogicalMin = %ld\n", cap_idx, pp_cap->NotButton.LogicalMin); 73 fprintf(file, "pp_data->cap[%u]->NotButton.LogicalMax = %ld\n", cap_idx, pp_cap->NotButton.LogicalMax); 74 fprintf(file, "pp_data->cap[%u]->NotButton.PhysicalMin = %ld\n", cap_idx, pp_cap->NotButton.PhysicalMin); 75 fprintf(file, "pp_data->cap[%u]->NotButton.PhysicalMax = %ld\n", cap_idx, pp_cap->NotButton.PhysicalMax); 76 }; 77 fprintf(file, "pp_data->cap[%u]->Units = %lu\n", cap_idx, pp_cap->Units); 78 fprintf(file, "pp_data->cap[%u]->UnitsExp = %lu\n", cap_idx, pp_cap->UnitsExp); 79} 80 81void dump_hidp_link_collection_node(FILE* file, phid_pp_link_collection_node pcoll, unsigned int coll_idx) { 82 fprintf(file, "pp_data->LinkCollectionArray[%u]->LinkUsage = 0x%04hX\n", coll_idx, pcoll->LinkUsage); 83 fprintf(file, "pp_data->LinkCollectionArray[%u]->LinkUsagePage = 0x%04hX\n", coll_idx, pcoll->LinkUsagePage); 84 fprintf(file, "pp_data->LinkCollectionArray[%u]->Parent = %hu\n", coll_idx, pcoll->Parent); 85 fprintf(file, "pp_data->LinkCollectionArray[%u]->NumberOfChildren = %hu\n", coll_idx, pcoll->NumberOfChildren); 86 fprintf(file, "pp_data->LinkCollectionArray[%u]->NextSibling = %hu\n", coll_idx, pcoll->NextSibling); 87 fprintf(file, "pp_data->LinkCollectionArray[%u]->FirstChild = %hu\n", coll_idx, pcoll->FirstChild); 88 // The compilers are not consistent on ULONG-bit-fields: They lose the unsinged or define them as int. 89 // Thus just always cast them to unsinged int, which should be fine, as the biggest bit-field is 28 bit 90 fprintf(file, "pp_data->LinkCollectionArray[%u]->CollectionType = %u\n", coll_idx, (unsigned int)(pcoll->CollectionType)); 91 fprintf(file, "pp_data->LinkCollectionArray[%u]->IsAlias = %u\n", coll_idx, (unsigned int)(pcoll->IsAlias)); 92 fprintf(file, "pp_data->LinkCollectionArray[%u]->Reserved = 0x%08X\n", coll_idx, (unsigned int)(pcoll->Reserved)); 93} 94 95int dump_pp_data(FILE* file, hid_device* dev) 96{ 97 BOOL res; 98 hidp_preparsed_data* pp_data = NULL; 99 100 res = HidD_GetPreparsedData(dev->device_handle, (PHIDP_PREPARSED_DATA*) &pp_data); 101 if (!res) { 102 printf("ERROR: HidD_GetPreparsedData failed!"); 103 return -1; 104 } 105 else { 106 fprintf(file, "pp_data->MagicKey = 0x%02hhX%02hhX%02hhX%02hhX%02hhX%02hhX%02hhX%02hhX\n", pp_data->MagicKey[0], pp_data->MagicKey[1], pp_data->MagicKey[2], pp_data->MagicKey[3], pp_data->MagicKey[4], pp_data->MagicKey[5], pp_data->MagicKey[6], pp_data->MagicKey[7]); 107 fprintf(file, "pp_data->Usage = 0x%04hX\n", pp_data->Usage); 108 fprintf(file, "pp_data->UsagePage = 0x%04hX\n", pp_data->UsagePage); 109 fprintf(file, "pp_data->Reserved = 0x%04hX%04hX\n", pp_data->Reserved[0], pp_data->Reserved[1]); 110 fprintf(file, "# Input caps_info struct:\n"); 111 fprintf(file, "pp_data->caps_info[0]->FirstCap = %hu\n", pp_data->caps_info[0].FirstCap); 112 fprintf(file, "pp_data->caps_info[0]->LastCap = %hu\n", pp_data->caps_info[0].LastCap); 113 fprintf(file, "pp_data->caps_info[0]->NumberOfCaps = %hu\n", pp_data->caps_info[0].NumberOfCaps); 114 fprintf(file, "pp_data->caps_info[0]->ReportByteLength = %hu\n", pp_data->caps_info[0].ReportByteLength); 115 fprintf(file, "# Output caps_info struct:\n"); 116 fprintf(file, "pp_data->caps_info[1]->FirstCap = %hu\n", pp_data->caps_info[1].FirstCap); 117 fprintf(file, "pp_data->caps_info[1]->LastCap = %hu\n", pp_data->caps_info[1].LastCap); 118 fprintf(file, "pp_data->caps_info[1]->NumberOfCaps = %hu\n", pp_data->caps_info[1].NumberOfCaps); 119 fprintf(file, "pp_data->caps_info[1]->ReportByteLength = %hu\n", pp_data->caps_info[1].ReportByteLength); 120 fprintf(file, "# Feature caps_info struct:\n"); 121 fprintf(file, "pp_data->caps_info[2]->FirstCap = %hu\n", pp_data->caps_info[2].FirstCap); 122 fprintf(file, "pp_data->caps_info[2]->LastCap = %hu\n", pp_data->caps_info[2].LastCap); 123 fprintf(file, "pp_data->caps_info[2]->NumberOfCaps = %hu\n", pp_data->caps_info[2].NumberOfCaps); 124 fprintf(file, "pp_data->caps_info[2]->ReportByteLength = %hu\n", pp_data->caps_info[2].ReportByteLength); 125 fprintf(file, "# LinkCollectionArray Offset & Size:\n"); 126 fprintf(file, "pp_data->FirstByteOfLinkCollectionArray = 0x%04hX\n", pp_data->FirstByteOfLinkCollectionArray); 127 fprintf(file, "pp_data->NumberLinkCollectionNodes = %hu\n", pp_data->NumberLinkCollectionNodes); 128 129 130 phid_pp_cap pcap = (phid_pp_cap)(((unsigned char*)pp_data) + offsetof(hidp_preparsed_data, caps)); 131 fprintf(file, "# Input hid_pp_cap struct:\n"); 132 for (int caps_idx = pp_data->caps_info[0].FirstCap; caps_idx < pp_data->caps_info[0].LastCap; caps_idx++) { 133 dump_hid_pp_cap(file, pcap + caps_idx, caps_idx); 134 fprintf(file, "\n"); 135 } 136 fprintf(file, "# Output hid_pp_cap struct:\n"); 137 for (int caps_idx = pp_data->caps_info[1].FirstCap; caps_idx < pp_data->caps_info[1].LastCap; caps_idx++) { 138 dump_hid_pp_cap(file, pcap + caps_idx, caps_idx); 139 fprintf(file, "\n"); 140 } 141 fprintf(file, "# Feature hid_pp_cap struct:\n"); 142 for (int caps_idx = pp_data->caps_info[2].FirstCap; caps_idx < pp_data->caps_info[2].LastCap; caps_idx++) { 143 dump_hid_pp_cap(file, pcap + caps_idx, caps_idx); 144 fprintf(file, "\n"); 145 } 146 147 phid_pp_link_collection_node pcoll = (phid_pp_link_collection_node)(((unsigned char*)pcap) + pp_data->FirstByteOfLinkCollectionArray); 148 fprintf(file, "# Link Collections:\n"); 149 for (int coll_idx = 0; coll_idx < pp_data->NumberLinkCollectionNodes; coll_idx++) { 150 dump_hidp_link_collection_node(file, pcoll + coll_idx, coll_idx); 151 } 152 153 HidD_FreePreparsedData((PHIDP_PREPARSED_DATA) pp_data); 154 return 0; 155 } 156} 157 158int main(int argc, char* argv[]) 159{ 160 (void)argc; 161 (void)argv; 162 163 #define MAX_STR 255 164 165 struct hid_device_info *devs, *cur_dev; 166 167 printf("pp_data_dump tool. Compiled with hidapi version %s, runtime version %s.\n", HID_API_VERSION_STR, hid_version_str()); 168 if (hid_version()->major == HID_API_VERSION_MAJOR && hid_version()->minor == HID_API_VERSION_MINOR && hid_version()->patch == HID_API_VERSION_PATCH) { 169 printf("Compile-time version matches runtime version of hidapi.\n\n"); 170 } 171 else { 172 printf("Compile-time version is different than runtime version of hidapi.\n]n"); 173 } 174 175 if (hid_init()) 176 return -1; 177 178 devs = hid_enumerate(0x0, 0x0); 179 cur_dev = devs; 180 while (cur_dev) { 181 printf("Device Found\n type: %04hx %04hx\n path: %s\n serial_number: %ls", cur_dev->vendor_id, cur_dev->product_id, cur_dev->path, cur_dev->serial_number); 182 printf("\n"); 183 printf(" Manufacturer: %ls\n", cur_dev->manufacturer_string); 184 printf(" Product: %ls\n", cur_dev->product_string); 185 printf(" Release: %hX\n", cur_dev->release_number); 186 printf(" Interface: %d\n", cur_dev->interface_number); 187 printf(" Usage (page): %02X (%02X)\n", cur_dev->usage, cur_dev->usage_page); 188 189 hid_device *device = hid_open_path(cur_dev->path); 190 if (device) { 191 char filename[MAX_STR]; 192 FILE* file; 193 194 sprintf_s(filename, MAX_STR, "%04X_%04X_%04X_%04X.pp_data", cur_dev->vendor_id, cur_dev->product_id, cur_dev->usage, cur_dev->usage_page); 195 errno_t err = fopen_s(&file, filename, "w"); 196 if (err == 0) { 197 fprintf(file, "# HIDAPI device info struct:\n"); 198 fprintf(file, "dev->vendor_id = 0x%04hX\n", cur_dev->vendor_id); 199 fprintf(file, "dev->product_id = 0x%04hX\n", cur_dev->product_id); 200 fprintf(file, "dev->manufacturer_string = \"%ls\"\n", cur_dev->manufacturer_string); 201 fprintf(file, "dev->product_string = \"%ls\"\n", cur_dev->product_string); 202 fprintf(file, "dev->release_number = 0x%04hX\n", cur_dev->release_number); 203 fprintf(file, "dev->interface_number = %d\n", cur_dev->interface_number); 204 fprintf(file, "dev->usage = 0x%04hX\n", cur_dev->usage); 205 fprintf(file, "dev->usage_page = 0x%04hX\n", cur_dev->usage_page); 206 fprintf(file, "dev->path = \"%s\"\n", cur_dev->path); 207 fprintf(file, "\n# Preparsed Data struct:\n"); 208 int res = dump_pp_data(file, device); 209 210 if (res == 0) { 211 printf("Dumped Preparsed Data to %s\n", filename); 212 } 213 else { 214 printf("ERROR: Dump Preparsed Data to %s failed!\n", filename); 215 } 216 217 fclose(file); 218 } 219 220 hid_close(device); 221 } 222 else { 223 printf(" Device: not available.\n"); 224 } 225 226 printf("\n"); 227 cur_dev = cur_dev->next; 228 } 229 hid_free_enumeration(devs); 230 231 232 /* Free static HIDAPI objects. */ 233 hid_exit(); 234 235 //system("pause"); 236 237 return 0; 238} 239[FILE END](C) 2025 0x4248 (C) 2025 4248 Media and 4248 Systems, All part of 0x4248 See LICENCE files for more information. Not all files are by 0x4248 always check Licencing.