2 Helper functions to parse HID report descriptor and items.
4 Copyright (c) 2004 - 2010, Intel Corporation. All rights reserved.<BR>
5 SPDX-License-Identifier: BSD-2-Clause-Patent
9 #include "UsbMouseAbsolutePointer.h"
13 Get next HID item from report descriptor.
15 This function retrieves next HID item from report descriptor, according to
17 According to USB HID Specification, An item is piece of information
18 about the device. All items have a one-byte prefix that contains
19 the item tag, item type, and item size.
20 There are two basic types of items: short items and long items.
21 If the item is a short item, its optional data size may be 0, 1, 2, or 4 bytes.
22 Only short item is supported here.
24 @param StartPos Start position of the HID item to get.
25 @param EndPos End position of the range to get the the next HID item.
26 @param HidItem Buffer for the HID Item to return.
28 @return Pointer to end of the HID item returned.
29 NULL if no HID item retrieved.
41 if (EndPos
<= StartPos
) {
49 // Bit format of prefix byte:
54 HidItem
->Type
= BitFieldRead8 (Temp
, 2, 3);
55 HidItem
->Tag
= BitFieldRead8 (Temp
, 4, 7);
57 if (HidItem
->Tag
== HID_ITEM_TAG_LONG
) {
59 // Long Items are not supported, although we try to parse it.
61 HidItem
->Format
= HID_ITEM_FORMAT_LONG
;
63 if ((EndPos
- StartPos
) >= 2) {
64 HidItem
->Size
= *StartPos
++;
65 HidItem
->Tag
= *StartPos
++;
67 if ((EndPos
- StartPos
) >= HidItem
->Size
) {
68 HidItem
->Data
.LongData
= StartPos
;
69 StartPos
+= HidItem
->Size
;
74 HidItem
->Format
= HID_ITEM_FORMAT_SHORT
;
75 HidItem
->Size
= BitFieldRead8 (Temp
, 0, 1);
77 switch (HidItem
->Size
) {
88 if ((EndPos
- StartPos
) >= 1) {
89 HidItem
->Data
.Uint8
= *StartPos
++;
97 if ((EndPos
- StartPos
) >= 2) {
98 CopyMem (&HidItem
->Data
.Uint16
, StartPos
, sizeof (UINT16
));
105 // 4-byte data, adjust size
108 if ((EndPos
- StartPos
) >= 4) {
109 CopyMem (&HidItem
->Data
.Uint32
, StartPos
, sizeof (UINT32
));
121 Get data from HID item.
123 This function retrieves data from HID item.
124 It only supports short items, which has 4 types of data:
127 @param HidItem Pointer to the HID item.
129 @return The data of HID item.
138 // Get data from HID item.
140 switch (HidItem
->Size
) {
142 return HidItem
->Data
.Uint8
;
144 return HidItem
->Data
.Uint16
;
146 return HidItem
->Data
.Uint32
;
152 Parse HID item from report descriptor.
154 There are three item types: Main, Global, and Local.
155 This function parses these types of HID items according
158 @param UsbMouse The instance of USB_MOUSE_ABSOLUTE_POINTER_DEV
159 @param HidItem The HID item to parse
164 IN USB_MOUSE_ABSOLUTE_POINTER_DEV
*UsbMouse
,
170 switch (HidItem
->Type
) {
172 case HID_ITEM_TYPE_MAIN
:
174 // we don't care any main items, just skip
178 case HID_ITEM_TYPE_GLOBAL
:
180 // For global items, we only care Usage Page tag for Button Page here
182 if (HidItem
->Tag
== HID_GLOBAL_ITEM_TAG_USAGE_PAGE
) {
183 Data
= (UINT8
) GetItemData (HidItem
);
188 UsbMouse
->PrivateData
.ButtonDetected
= TRUE
;
193 case HID_ITEM_TYPE_LOCAL
:
194 if (HidItem
->Size
== 0) {
196 // No expected data for local item
201 Data
= (UINT8
) GetItemData (HidItem
);
203 switch (HidItem
->Tag
) {
204 case HID_LOCAL_ITEM_TAG_USAGE_MINIMUM
:
205 if (UsbMouse
->PrivateData
.ButtonDetected
) {
206 UsbMouse
->PrivateData
.ButtonMinIndex
= Data
;
210 case HID_LOCAL_ITEM_TAG_USAGE_MAXIMUM
:
212 if (UsbMouse
->PrivateData
.ButtonDetected
) {
213 UsbMouse
->PrivateData
.ButtonMaxIndex
= Data
;
226 Parse Mouse Report Descriptor.
228 According to USB HID Specification, report descriptors are
229 composed of pieces of information. Each piece of information
230 is called an Item. This function retrieves each item from
231 the report descriptor and updates USB_MOUSE_ABSOLUTE_POINTER_DEV.
233 @param UsbMouseAbsolutePointer The instance of USB_MOUSE_ABSOLUTE_POINTER_DEV
234 @param ReportDescriptor Report descriptor to parse
235 @param ReportSize Report descriptor size
237 @retval EFI_SUCCESS Report descriptor successfully parsed.
238 @retval EFI_UNSUPPORTED Report descriptor contains long item.
242 ParseMouseReportDescriptor (
243 OUT USB_MOUSE_ABSOLUTE_POINTER_DEV
*UsbMouseAbsolutePointer
,
244 IN UINT8
*ReportDescriptor
,
248 UINT8
*DescriptorEnd
;
252 DescriptorEnd
= ReportDescriptor
+ ReportSize
;
254 Ptr
= GetNextHidItem (ReportDescriptor
, DescriptorEnd
, &HidItem
);
255 while (Ptr
!= NULL
) {
256 if (HidItem
.Format
!= HID_ITEM_FORMAT_SHORT
) {
258 // Long Item is not supported at current HID revision
260 return EFI_UNSUPPORTED
;
263 ParseHidItem (UsbMouseAbsolutePointer
, &HidItem
);
265 Ptr
= GetNextHidItem (Ptr
, DescriptorEnd
, &HidItem
);
268 UsbMouseAbsolutePointer
->NumberOfButtons
= (UINT8
) (UsbMouseAbsolutePointer
->PrivateData
.ButtonMaxIndex
- UsbMouseAbsolutePointer
->PrivateData
.ButtonMinIndex
+ 1);
269 UsbMouseAbsolutePointer
->XLogicMax
= 1023;
270 UsbMouseAbsolutePointer
->YLogicMax
= 1023;
271 UsbMouseAbsolutePointer
->XLogicMin
= -1023;
272 UsbMouseAbsolutePointer
->YLogicMin
= -1023;