2 * Common controller functions and structures
4 * Copyright 2018 Aric Stewart
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21 /* Blocks of data for building HID device descriptions */
23 static const BYTE REPORT_HEADER
[] = {
24 0x05, 0x01, /* USAGE_PAGE (Generic Desktop) */
25 0x09, 0x00, /* USAGE (??) */
26 0xa1, 0x01, /* COLLECTION (Application) */
27 0x09, 0x01, /* USAGE () */
28 0xa1, 0x00, /* COLLECTION (Physical) */
30 #define IDX_HEADER_PAGE 1
31 #define IDX_HEADER_USAGE 3
33 static const BYTE REPORT_BUTTONS
[] = {
34 0x05, 0x09, /* USAGE_PAGE (Button) */
35 0x19, 0x01, /* USAGE_MINIMUM (Button 1) */
36 0x29, 0x03, /* USAGE_MAXIMUM (Button 3) */
37 0x15, 0x00, /* LOGICAL_MINIMUM (0) */
38 0x25, 0x01, /* LOGICAL_MAXIMUM (1) */
39 0x35, 0x00, /* PHYSICAL_MINIMUM (0) */
40 0x45, 0x01, /* PHYSICAL_MAXIMUM (1) */
41 0x95, 0x03, /* REPORT_COUNT (3) */
42 0x75, 0x01, /* REPORT_SIZE (1) */
43 0x81, 0x02, /* INPUT (Data,Var,Abs) */
45 #define IDX_BUTTON_MIN_USAGE 3
46 #define IDX_BUTTON_MAX_USAGE 5
47 #define IDX_BUTTON_COUNT 15
49 static const BYTE REPORT_PADDING
[] = {
50 0x95, 0x03, /* REPORT_COUNT (3) */
51 0x75, 0x01, /* REPORT_SIZE (1) */
52 0x81, 0x03, /* INPUT (Cnst,Var,Abs) */
54 #define IDX_PADDING_BIT_COUNT 1
56 static const BYTE REPORT_AXIS_HEADER
[] = {
57 0x05, 0x01, /* USAGE_PAGE (Generic Desktop) */
59 #define IDX_AXIS_PAGE 1
61 static const BYTE REPORT_AXIS_USAGE
[] = {
62 0x09, 0x30, /* USAGE (X) */
64 #define IDX_AXIS_USAGE 1
66 static const BYTE REPORT_REL_AXIS_TAIL
[] = {
67 0x15, 0x81, /* LOGICAL_MINIMUM (0) */
68 0x25, 0x7f, /* LOGICAL_MAXIMUM (0xffff) */
69 0x75, 0x08, /* REPORT_SIZE (16) */
70 0x95, 0x02, /* REPORT_COUNT (2) */
71 0x81, 0x06, /* INPUT (Data,Var,Rel) */
73 #define IDX_REL_AXIS_COUNT 7
75 static const BYTE REPORT_HATSWITCH
[] = {
76 0x05, 0x01, /* USAGE_PAGE (Generic Desktop) */
77 0x09, 0x39, /* USAGE (Hatswitch) */
78 0x15, 0x01, /* LOGICAL_MINIMUM (1) */
79 0x25, 0x08, /* LOGICAL_MAXIMUM (0x08) */
80 0x35, 0x00, /* PHYSICAL_MINIMUM (0) */
81 0x45, 0x08, /* PHYSICAL_MAXIMUM (8) */
82 0x75, 0x04, /* REPORT_SIZE (4) */
83 0x95, 0x01, /* REPORT_COUNT (1) */
84 0x81, 0x02, /* INPUT (Data,Var,Abs) */
86 #define IDX_HATSWITCH_COUNT 15
88 static const BYTE REPORT_TAIL
[] = {
89 0xc0, /* END_COLLECTION */
90 0xc0 /* END_COLLECTION */
93 static inline BYTE
*add_button_block(BYTE
* report_ptr
, BYTE usage_min
, BYTE usage_max
)
95 memcpy(report_ptr
, REPORT_BUTTONS
, sizeof(REPORT_BUTTONS
));
96 report_ptr
[IDX_BUTTON_MIN_USAGE
] = usage_min
;
97 report_ptr
[IDX_BUTTON_MAX_USAGE
] = usage_max
;
98 report_ptr
[IDX_BUTTON_COUNT
] = (usage_max
- usage_min
) + 1;
99 return report_ptr
+ sizeof(REPORT_BUTTONS
);
103 static inline BYTE
*add_padding_block(BYTE
*report_ptr
, BYTE bitcount
)
105 memcpy(report_ptr
, REPORT_PADDING
, sizeof(REPORT_PADDING
));
106 report_ptr
[IDX_PADDING_BIT_COUNT
] = bitcount
;
107 return report_ptr
+ sizeof(REPORT_PADDING
);
110 static inline BYTE
*add_hatswitch(BYTE
*report_ptr
, INT count
)
112 memcpy(report_ptr
, REPORT_HATSWITCH
, sizeof(REPORT_HATSWITCH
));
113 report_ptr
[IDX_HATSWITCH_COUNT
] = count
;
114 return report_ptr
+ sizeof(REPORT_HATSWITCH
);