12b4464b0SVladimir Kondratyev /*- 22b4464b0SVladimir Kondratyev * Copyright (c) 2019 Vladimir Kondratyev <wulf@FreeBSD.org> 32b4464b0SVladimir Kondratyev * 42b4464b0SVladimir Kondratyev * Redistribution and use in source and binary forms, with or without 52b4464b0SVladimir Kondratyev * modification, are permitted provided that the following conditions 62b4464b0SVladimir Kondratyev * are met: 72b4464b0SVladimir Kondratyev * 1. Redistributions of source code must retain the above copyright 82b4464b0SVladimir Kondratyev * notice, this list of conditions and the following disclaimer. 92b4464b0SVladimir Kondratyev * 2. Redistributions in binary form must reproduce the above copyright 102b4464b0SVladimir Kondratyev * notice, this list of conditions and the following disclaimer in the 112b4464b0SVladimir Kondratyev * documentation and/or other materials provided with the distribution. 122b4464b0SVladimir Kondratyev * 132b4464b0SVladimir Kondratyev * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 142b4464b0SVladimir Kondratyev * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 152b4464b0SVladimir Kondratyev * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 162b4464b0SVladimir Kondratyev * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 172b4464b0SVladimir Kondratyev * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 182b4464b0SVladimir Kondratyev * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 192b4464b0SVladimir Kondratyev * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 202b4464b0SVladimir Kondratyev * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 212b4464b0SVladimir Kondratyev * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 222b4464b0SVladimir Kondratyev * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 232b4464b0SVladimir Kondratyev * SUCH DAMAGE. 242b4464b0SVladimir Kondratyev */ 252b4464b0SVladimir Kondratyev 262b4464b0SVladimir Kondratyev #ifndef _HID_HIDBUS_H_ 272b4464b0SVladimir Kondratyev #define _HID_HIDBUS_H_ 282b4464b0SVladimir Kondratyev 292b4464b0SVladimir Kondratyev enum { 302b4464b0SVladimir Kondratyev HIDBUS_IVAR_USAGE, 312b4464b0SVladimir Kondratyev HIDBUS_IVAR_INDEX, 322b4464b0SVladimir Kondratyev HIDBUS_IVAR_FLAGS, 332b4464b0SVladimir Kondratyev #define HIDBUS_FLAG_AUTOCHILD (0<<1) /* Child is autodiscovered */ 342b4464b0SVladimir Kondratyev #define HIDBUS_FLAG_CAN_POLL (1<<1) /* Child can work during panic */ 352b4464b0SVladimir Kondratyev HIDBUS_IVAR_DRIVER_INFO, 362b4464b0SVladimir Kondratyev HIDBUS_IVAR_LOCK, 372b4464b0SVladimir Kondratyev }; 382b4464b0SVladimir Kondratyev 392b4464b0SVladimir Kondratyev #define HIDBUS_ACCESSOR(A, B, T) \ 402b4464b0SVladimir Kondratyev __BUS_ACCESSOR(hidbus, A, HIDBUS, B, T) 412b4464b0SVladimir Kondratyev 422b4464b0SVladimir Kondratyev HIDBUS_ACCESSOR(usage, USAGE, int32_t) 432b4464b0SVladimir Kondratyev HIDBUS_ACCESSOR(index, INDEX, uint8_t) 442b4464b0SVladimir Kondratyev HIDBUS_ACCESSOR(flags, FLAGS, uint32_t) 452b4464b0SVladimir Kondratyev HIDBUS_ACCESSOR(driver_info, DRIVER_INFO, uintptr_t) 462b4464b0SVladimir Kondratyev HIDBUS_ACCESSOR(lock, LOCK, struct mtx *) 472b4464b0SVladimir Kondratyev 482b4464b0SVladimir Kondratyev /* 492b4464b0SVladimir Kondratyev * The following structure is used when looking up an HID driver for 502b4464b0SVladimir Kondratyev * an HID device. It is inspired by the structure called "usb_device_id". 512b4464b0SVladimir Kondratyev * which is originated in Linux and ported to FreeBSD. 522b4464b0SVladimir Kondratyev */ 532b4464b0SVladimir Kondratyev struct hid_device_id { 542b4464b0SVladimir Kondratyev 552b4464b0SVladimir Kondratyev /* Select which fields to match against */ 562b4464b0SVladimir Kondratyev #if BYTE_ORDER == LITTLE_ENDIAN 572b4464b0SVladimir Kondratyev uint16_t 582b4464b0SVladimir Kondratyev match_flag_page:1, 592b4464b0SVladimir Kondratyev match_flag_usage:1, 602b4464b0SVladimir Kondratyev match_flag_bus:1, 612b4464b0SVladimir Kondratyev match_flag_vendor:1, 622b4464b0SVladimir Kondratyev match_flag_product:1, 632b4464b0SVladimir Kondratyev match_flag_ver_lo:1, 642b4464b0SVladimir Kondratyev match_flag_ver_hi:1, 652b4464b0SVladimir Kondratyev match_flag_pnp:1, 662b4464b0SVladimir Kondratyev match_flag_unused:8; 672b4464b0SVladimir Kondratyev #else 682b4464b0SVladimir Kondratyev uint16_t 692b4464b0SVladimir Kondratyev match_flag_unused:8, 702b4464b0SVladimir Kondratyev match_flag_pnp:1, 712b4464b0SVladimir Kondratyev match_flag_ver_hi:1, 722b4464b0SVladimir Kondratyev match_flag_ver_lo:1, 732b4464b0SVladimir Kondratyev match_flag_product:1, 742b4464b0SVladimir Kondratyev match_flag_vendor:1, 752b4464b0SVladimir Kondratyev match_flag_bus:1, 762b4464b0SVladimir Kondratyev match_flag_usage:1, 772b4464b0SVladimir Kondratyev match_flag_page:1; 782b4464b0SVladimir Kondratyev #endif 792b4464b0SVladimir Kondratyev 802b4464b0SVladimir Kondratyev /* Used for top level collection usage matches */ 812b4464b0SVladimir Kondratyev uint16_t page; 822b4464b0SVladimir Kondratyev uint16_t usage; 832b4464b0SVladimir Kondratyev 842b4464b0SVladimir Kondratyev /* Used for product specific matches; the Version range is inclusive */ 852b4464b0SVladimir Kondratyev uint8_t idBus; 862b4464b0SVladimir Kondratyev uint16_t idVendor; 872b4464b0SVladimir Kondratyev uint16_t idProduct; 882b4464b0SVladimir Kondratyev uint16_t idVersion_lo; 892b4464b0SVladimir Kondratyev uint16_t idVersion_hi; 902b4464b0SVladimir Kondratyev char *idPnP; 912b4464b0SVladimir Kondratyev 922b4464b0SVladimir Kondratyev /* Hook for driver specific information */ 932b4464b0SVladimir Kondratyev uintptr_t driver_info; 942b4464b0SVladimir Kondratyev }; 952b4464b0SVladimir Kondratyev 962b4464b0SVladimir Kondratyev #define HID_STD_PNP_INFO \ 972b4464b0SVladimir Kondratyev "M16:mask;U16:page;U16:usage;U8:bus;U16:vendor;U16:product;" \ 982b4464b0SVladimir Kondratyev "L16:version;G16:version;Z:_HID" 992b4464b0SVladimir Kondratyev #define HID_PNP_INFO(table) \ 1002b4464b0SVladimir Kondratyev MODULE_PNP_INFO(HID_STD_PNP_INFO, hidbus, table, table, nitems(table)) 1012b4464b0SVladimir Kondratyev 1022b4464b0SVladimir Kondratyev #define HID_TLC(pg,usg) \ 1032b4464b0SVladimir Kondratyev .match_flag_page = 1, .match_flag_usage = 1, .page = (pg), .usage = (usg) 1042b4464b0SVladimir Kondratyev 1052b4464b0SVladimir Kondratyev #define HID_BUS(bus) \ 1062b4464b0SVladimir Kondratyev .match_flag_bus = 1, .idBus = (bus) 1072b4464b0SVladimir Kondratyev 1082b4464b0SVladimir Kondratyev #define HID_VENDOR(vend) \ 1092b4464b0SVladimir Kondratyev .match_flag_vendor = 1, .idVendor = (vend) 1102b4464b0SVladimir Kondratyev 1112b4464b0SVladimir Kondratyev #define HID_PRODUCT(prod) \ 1122b4464b0SVladimir Kondratyev .match_flag_product = 1, .idProduct = (prod) 1132b4464b0SVladimir Kondratyev 1142b4464b0SVladimir Kondratyev #define HID_VP(vend,prod) \ 1152b4464b0SVladimir Kondratyev HID_VENDOR(vend), HID_PRODUCT(prod) 1162b4464b0SVladimir Kondratyev 1172b4464b0SVladimir Kondratyev #define HID_BVP(bus,vend,prod) \ 1182b4464b0SVladimir Kondratyev HID_BUS(bus), HID_VENDOR(vend), HID_PRODUCT(prod) 1192b4464b0SVladimir Kondratyev 1202b4464b0SVladimir Kondratyev #define HID_BVPI(bus,vend,prod,info) \ 1212b4464b0SVladimir Kondratyev HID_BUS(bus), HID_VENDOR(vend), HID_PRODUCT(prod), HID_DRIVER_INFO(info) 1222b4464b0SVladimir Kondratyev 1232b4464b0SVladimir Kondratyev #define HID_VERSION_GTEQ(lo) /* greater than or equal */ \ 1242b4464b0SVladimir Kondratyev .match_flag_ver_lo = 1, .idVersion_lo = (lo) 1252b4464b0SVladimir Kondratyev 1262b4464b0SVladimir Kondratyev #define HID_VERSION_LTEQ(hi) /* less than or equal */ \ 1272b4464b0SVladimir Kondratyev .match_flag_ver_hi = 1, .idVersion_hi = (hi) 1282b4464b0SVladimir Kondratyev 1292b4464b0SVladimir Kondratyev #define HID_PNP(pnp) \ 1302b4464b0SVladimir Kondratyev .match_flag_pnp = 1, .idPnP = (pnp) 1312b4464b0SVladimir Kondratyev 1322b4464b0SVladimir Kondratyev #define HID_DRIVER_INFO(n) \ 1332b4464b0SVladimir Kondratyev .driver_info = (n) 1342b4464b0SVladimir Kondratyev 1352b4464b0SVladimir Kondratyev #define HID_GET_DRIVER_INFO(did) \ 1362b4464b0SVladimir Kondratyev (did)->driver_info 1372b4464b0SVladimir Kondratyev 1382b4464b0SVladimir Kondratyev #define HIDBUS_LOOKUP_ID(d, h) hidbus_lookup_id((d), (h), nitems(h)) 1392b4464b0SVladimir Kondratyev #define HIDBUS_LOOKUP_DRIVER_INFO(d, h) \ 1402b4464b0SVladimir Kondratyev hidbus_lookup_driver_info((d), (h), nitems(h)) 1412b4464b0SVladimir Kondratyev 1422b4464b0SVladimir Kondratyev /* 1432b4464b0SVladimir Kondratyev * Walk through all HID items hi belonging Top Level Collection #tlc_index 1442b4464b0SVladimir Kondratyev */ 1452b4464b0SVladimir Kondratyev #define HIDBUS_FOREACH_ITEM(hd, hi, tlc_index) \ 1462b4464b0SVladimir Kondratyev for (uint8_t _iter = 0; \ 1472b4464b0SVladimir Kondratyev _iter <= (tlc_index) && hid_get_item((hd), (hi)); \ 1482b4464b0SVladimir Kondratyev _iter += (hi)->kind == hid_endcollection && (hi)->collevel == 0) \ 1492b4464b0SVladimir Kondratyev if (_iter == (tlc_index)) 1502b4464b0SVladimir Kondratyev 1512b4464b0SVladimir Kondratyev int hidbus_locate(const void *desc, hid_size_t size, int32_t u, 1522b4464b0SVladimir Kondratyev enum hid_kind k, uint8_t tlc_index, uint8_t index, 1532b4464b0SVladimir Kondratyev struct hid_location *loc, uint32_t *flags, uint8_t *id, 1542b4464b0SVladimir Kondratyev struct hid_absinfo *ai); 155*d51e4376SVladimir Kondratyev bool hidbus_is_collection(const void *, hid_size_t, int32_t, uint8_t); 1562b4464b0SVladimir Kondratyev 1572b4464b0SVladimir Kondratyev const struct hid_device_id *hidbus_lookup_id(device_t, 1582b4464b0SVladimir Kondratyev const struct hid_device_id *, int); 1592b4464b0SVladimir Kondratyev struct hid_rdesc_info *hidbus_get_rdesc_info(device_t); 1602b4464b0SVladimir Kondratyev int hidbus_lookup_driver_info(device_t, 1612b4464b0SVladimir Kondratyev const struct hid_device_id *, int); 1622b4464b0SVladimir Kondratyev void hidbus_set_intr(device_t, hid_intr_t*, void *); 1632b4464b0SVladimir Kondratyev void hidbus_set_desc(device_t, const char *); 1642b4464b0SVladimir Kondratyev device_t hidbus_find_child(device_t, int32_t); 1652b4464b0SVladimir Kondratyev 1662b4464b0SVladimir Kondratyev /* hidbus HID interface */ 1672b4464b0SVladimir Kondratyev int hid_get_report_descr(device_t, void **, hid_size_t *); 1682b4464b0SVladimir Kondratyev int hid_set_report_descr(device_t, const void *, hid_size_t); 1692b4464b0SVladimir Kondratyev 1702b4464b0SVladimir Kondratyev const struct hid_device_info *hid_get_device_info(device_t); 1712b4464b0SVladimir Kondratyev 1722b4464b0SVladimir Kondratyev #endif /* _HID_HIDBUS_H_ */ 173