@@ -1544,13 +1544,12 @@ static inline int hid_array_value_is_valid(struct hid_field *field,
15441544}
15451545
15461546/*
1547- * Analyse a received field, and fetch the data from it. The field
1548- * content is stored for next report processing (we do differential
1549- * reporting to the layer).
1547+ * Fetch the field from the data. The field content is stored for next
1548+ * report processing (we do differential reporting to the layer).
15501549 */
1551-
1552- static void hid_input_field ( struct hid_device * hid , struct hid_field * field ,
1553- __u8 * data , int interrupt )
1550+ static void hid_input_fetch_field ( struct hid_device * hid ,
1551+ struct hid_field * field ,
1552+ __u8 * data )
15541553{
15551554 unsigned n ;
15561555 unsigned count = field -> report_count ;
@@ -1561,6 +1560,7 @@ static void hid_input_field(struct hid_device *hid, struct hid_field *field,
15611560
15621561 value = field -> new_value ;
15631562 memset (value , 0 , count * sizeof (__s32 ));
1563+ field -> ignored = false;
15641564
15651565 for (n = 0 ; n < count ; n ++ ) {
15661566
@@ -1572,21 +1572,56 @@ static void hid_input_field(struct hid_device *hid, struct hid_field *field,
15721572 /* Ignore report if ErrorRollOver */
15731573 if (!(field -> flags & HID_MAIN_ITEM_VARIABLE ) &&
15741574 hid_array_value_is_valid (field , value [n ]) &&
1575- field -> usage [value [n ] - min ].hid == HID_UP_KEYBOARD + 1 )
1575+ field -> usage [value [n ] - min ].hid == HID_UP_KEYBOARD + 1 ) {
1576+ field -> ignored = true;
15761577 return ;
1578+ }
15771579 }
1580+ }
15781581
1579- for (n = 0 ; n < count ; n ++ ) {
1582+ /*
1583+ * Process a received variable field.
1584+ */
15801585
1581- if (HID_MAIN_ITEM_VARIABLE & field -> flags ) {
1582- hid_process_event (hid ,
1583- field ,
1584- & field -> usage [n ],
1585- value [n ],
1586- interrupt );
1587- continue ;
1588- }
1586+ static void hid_input_var_field (struct hid_device * hid ,
1587+ struct hid_field * field ,
1588+ int interrupt )
1589+ {
1590+ unsigned int count = field -> report_count ;
1591+ __s32 * value = field -> new_value ;
1592+ unsigned int n ;
1593+
1594+ for (n = 0 ; n < count ; n ++ )
1595+ hid_process_event (hid ,
1596+ field ,
1597+ & field -> usage [n ],
1598+ value [n ],
1599+ interrupt );
1600+
1601+ memcpy (field -> value , value , count * sizeof (__s32 ));
1602+ }
15891603
1604+ /*
1605+ * Process a received array field. The field content is stored for
1606+ * next report processing (we do differential reporting to the layer).
1607+ */
1608+
1609+ static void hid_input_array_field (struct hid_device * hid ,
1610+ struct hid_field * field ,
1611+ int interrupt )
1612+ {
1613+ unsigned int n ;
1614+ unsigned int count = field -> report_count ;
1615+ __s32 min = field -> logical_minimum ;
1616+ __s32 * value ;
1617+
1618+ value = field -> new_value ;
1619+
1620+ /* ErrorRollOver */
1621+ if (field -> ignored )
1622+ return ;
1623+
1624+ for (n = 0 ; n < count ; n ++ ) {
15901625 if (hid_array_value_is_valid (field , field -> value [n ]) &&
15911626 search (value , field -> value [n ], count ))
15921627 hid_process_event (hid ,
@@ -1607,6 +1642,31 @@ static void hid_input_field(struct hid_device *hid, struct hid_field *field,
16071642 memcpy (field -> value , value , count * sizeof (__s32 ));
16081643}
16091644
1645+ /*
1646+ * Analyse a received report, and fetch the data from it. The field
1647+ * content is stored for next report processing (we do differential
1648+ * reporting to the layer).
1649+ */
1650+ static void hid_process_report (struct hid_device * hid ,
1651+ struct hid_report * report ,
1652+ __u8 * data ,
1653+ int interrupt )
1654+ {
1655+ unsigned int a ;
1656+ struct hid_field * field ;
1657+
1658+ for (a = 0 ; a < report -> maxfield ; a ++ ) {
1659+ field = report -> field [a ];
1660+
1661+ hid_input_fetch_field (hid , field , data );
1662+
1663+ if (field -> flags & HID_MAIN_ITEM_VARIABLE )
1664+ hid_input_var_field (hid , field , interrupt );
1665+ else
1666+ hid_input_array_field (hid , field , interrupt );
1667+ }
1668+ }
1669+
16101670/*
16111671 * Output the field into the report.
16121672 */
@@ -1768,7 +1828,6 @@ int hid_report_raw_event(struct hid_device *hid, int type, u8 *data, u32 size,
17681828 struct hid_report_enum * report_enum = hid -> report_enum + type ;
17691829 struct hid_report * report ;
17701830 struct hid_driver * hdrv ;
1771- unsigned int a ;
17721831 u32 rsize , csize = size ;
17731832 u8 * cdata = data ;
17741833 int ret = 0 ;
@@ -1804,8 +1863,7 @@ int hid_report_raw_event(struct hid_device *hid, int type, u8 *data, u32 size,
18041863 }
18051864
18061865 if (hid -> claimed != HID_CLAIMED_HIDRAW && report -> maxfield ) {
1807- for (a = 0 ; a < report -> maxfield ; a ++ )
1808- hid_input_field (hid , report -> field [a ], cdata , interrupt );
1866+ hid_process_report (hid , report , cdata , interrupt );
18091867 hdrv = hid -> driver ;
18101868 if (hdrv && hdrv -> report )
18111869 hdrv -> report (hid , report );
0 commit comments