internal unsafe static extern bool HidP_GetCaps( [In] byte *preparsedData, [In, Out] ref HIDP_CAPS caps);
internal unsafe CyHidReport(HIDP_REPORT_TYPE rType, HIDP_CAPS hidCaps, byte *PreparsedDta) { _rptType = rType; if (rType == HIDP_REPORT_TYPE.HidP_Input) { _RptByteLen = hidCaps.InputReportByteLength; _NumBtnCaps = hidCaps.NumberInputButtonCaps; _NumValCaps = hidCaps.NumberInputValueCaps; } else if (rType == HIDP_REPORT_TYPE.HidP_Output) { _RptByteLen = hidCaps.OutputReportByteLength; _NumBtnCaps = hidCaps.NumberOutputButtonCaps; _NumValCaps = hidCaps.NumberOutputValueCaps; } else { _RptByteLen = hidCaps.FeatureReportByteLength; _NumBtnCaps = hidCaps.NumberFeatureButtonCaps; _NumValCaps = hidCaps.NumberFeatureValueCaps; } // Big enough to hold the report ID and the report data if (_RptByteLen > 0) { DataBuf = new byte[_RptByteLen + 1]; } if (_NumBtnCaps > 0) { HIDP_BTN_VAL_CAPS ButtonCaps; Buttons = new CyHidButton[_NumBtnCaps]; HIDP_BTN_VAL_CAPS bc = new HIDP_BTN_VAL_CAPS(); byte[] buffer = new byte[_NumBtnCaps * Marshal.SizeOf(bc)]; fixed(byte *buf = buffer) { int numCaps = _NumBtnCaps; // // BUGFIX 3/07/2008 - HidP_GetButtonCaps will modify numCaps to the // "actual number of elements that the routine returns". // In the somewhat rare event that numcaps is < _NumBtnCaps // on return, the reference to bCaps[i] in the loop below // will throw an "Index Was Outside the Bounds of the Array" // Exception. This would occur for example when the // top-level HID report (being reported here) contains // a subset of the available buttons in the full HID interface. // PInvoke.HidP_GetButtonCaps(rType, buf, ref numCaps, PreparsedDta); // // Reset _NumBtnCaps to the actual returned value. // _NumBtnCaps = numCaps; HIDP_BTN_VAL_CAPS *bCaps = (HIDP_BTN_VAL_CAPS *)buf; for (int i = 0; i < _NumBtnCaps; i++) { // This assignment copies values from buf into ButtonCaps. ButtonCaps = bCaps[i]; // Note that you must pass ButtonCaps to the // below constructor and not bCaps[i] Buttons[i] = new CyHidButton(ButtonCaps); // Each button should have the same ReportID _ReportID = ButtonCaps.ReportID; } } } if (_NumValCaps > 0) { Values = new CyHidValue[_NumValCaps]; HIDP_BTN_VAL_CAPS vc = new HIDP_BTN_VAL_CAPS(); byte[] buffer = new byte[_NumValCaps * Marshal.SizeOf(vc)]; fixed(byte *buf = buffer) { int numCaps = _NumValCaps; PInvoke.HidP_GetValueCaps(rType, buf, ref numCaps, PreparsedDta); HIDP_BTN_VAL_CAPS *vCaps = (HIDP_BTN_VAL_CAPS *)buf; for (int i = 0; i < _NumValCaps; i++) { // This assignment copies values from buf into ValueCaps. HIDP_BTN_VAL_CAPS ValueCaps = vCaps[i]; // Note that you must pass ValueCaps[i] to the // below constructor and not vCaps[i] Values[i] = new CyHidValue(ValueCaps); // Each value should have the same ReportID _ReportID = ValueCaps.ReportID; } } } _NumValues = 0; for (int i = 0; i < _NumValCaps; i++) { //if (Values[i].IsRange) // _NumValues += Values[i].UsageMax - Values[i].Usage + 1; //else _NumValues++; } _NumItems = _NumBtnCaps + _NumValues; if (_NumItems > 0) { Items = new HID_DATA[_NumItems]; } //if ((ButtonCaps != null) && (Items != null)) if ((_NumBtnCaps > 0) && (Items != null)) { for (int i = 0; i < _NumBtnCaps; i++) { Items[i].IsButtonData = 1; Items[i].Status = CyConst.HIDP_STATUS_SUCCESS; Items[i].UsagePage = Buttons[i].UsagePage; if (Buttons[i].IsRange) { Items[i].Usage = Buttons[i].Usage; Items[i].UsageMax = Buttons[i].UsageMax; } else { Items[i].Usage = Items[i].UsageMax = Buttons[i].Usage; } Items[i].MaxUsageLength = PInvoke.HidP_MaxUsageListLength( rType, Buttons[i].UsagePage, PreparsedDta); Items[i].Usages = new ushort[Items[i].MaxUsageLength]; Items[i].ReportID = Buttons[i].ReportID; } } for (int i = 0; i < _NumValues; i++) { if (Values[i].IsRange) { for (ushort usage = Values[i].Usage; usage <= Values[i].UsageMax; usage++) { Items[i].IsButtonData = 0; Items[i].Status = CyConst.HIDP_STATUS_SUCCESS; Items[i].UsagePage = Values[i].UsagePage; Items[i].Usage = usage; Items[i].ReportID = Values[i].ReportID; } } else { Items[i].IsButtonData = 0; Items[i].Status = CyConst.HIDP_STATUS_SUCCESS; Items[i].UsagePage = Values[i].UsagePage; Items[i].Usage = Values[i].Usage; Items[i].ReportID = Values[i].ReportID; } } } // End of CyHidReport constructor
internal unsafe CyHidReport(HIDP_REPORT_TYPE rType, HIDP_CAPS hidCaps, byte* PreparsedDta) { _rptType = rType; if (rType == HIDP_REPORT_TYPE.HidP_Input) { _RptByteLen = hidCaps.InputReportByteLength; _NumBtnCaps = hidCaps.NumberInputButtonCaps; _NumValCaps = hidCaps.NumberInputValueCaps; } else if (rType == HIDP_REPORT_TYPE.HidP_Output) { _RptByteLen = hidCaps.OutputReportByteLength; _NumBtnCaps = hidCaps.NumberOutputButtonCaps; _NumValCaps = hidCaps.NumberOutputValueCaps; } else { _RptByteLen = hidCaps.FeatureReportByteLength; _NumBtnCaps = hidCaps.NumberFeatureButtonCaps; _NumValCaps = hidCaps.NumberFeatureValueCaps; } // Big enough to hold the report ID and the report data if (_RptByteLen > 0) DataBuf = new byte[_RptByteLen + 1]; if (_NumBtnCaps > 0) { HIDP_BTN_VAL_CAPS ButtonCaps; Buttons = new CyHidButton[_NumBtnCaps]; HIDP_BTN_VAL_CAPS bc = new HIDP_BTN_VAL_CAPS(); byte[] buffer = new byte[_NumBtnCaps * Marshal.SizeOf(bc)]; fixed (byte* buf = buffer) { int numCaps = _NumBtnCaps; // // BUGFIX 3/07/2008 - HidP_GetButtonCaps will modify numCaps to the // "actual number of elements that the routine returns". // In the somewhat rare event that numcaps is < _NumBtnCaps // on return, the reference to bCaps[i] in the loop below // will throw an "Index Was Outside the Bounds of the Array" // Exception. This would occur for example when the // top-level HID report (being reported here) contains // a subset of the available buttons in the full HID interface. // PInvoke.HidP_GetButtonCaps(rType, buf, ref numCaps, PreparsedDta); // // Reset _NumBtnCaps to the actual returned value. // _NumBtnCaps = numCaps; HIDP_BTN_VAL_CAPS* bCaps = (HIDP_BTN_VAL_CAPS*)buf; for (int i = 0; i < _NumBtnCaps; i++) { // This assignment copies values from buf into ButtonCaps. ButtonCaps = bCaps[i]; // Note that you must pass ButtonCaps to the // below constructor and not bCaps[i] Buttons[i] = new CyHidButton(ButtonCaps); // Each button should have the same ReportID _ReportID = ButtonCaps.ReportID; } } } if (_NumValCaps > 0) { Values = new CyHidValue[_NumValCaps]; HIDP_BTN_VAL_CAPS vc = new HIDP_BTN_VAL_CAPS(); byte[] buffer = new byte[_NumValCaps * Marshal.SizeOf(vc)]; fixed (byte* buf = buffer) { int numCaps = _NumValCaps; PInvoke.HidP_GetValueCaps(rType, buf, ref numCaps, PreparsedDta); HIDP_BTN_VAL_CAPS* vCaps = (HIDP_BTN_VAL_CAPS*)buf; for (int i = 0; i < _NumValCaps; i++) { // This assignment copies values from buf into ValueCaps. HIDP_BTN_VAL_CAPS ValueCaps = vCaps[i]; // Note that you must pass ValueCaps[i] to the // below constructor and not vCaps[i] Values[i] = new CyHidValue(ValueCaps); // Each value should have the same ReportID _ReportID = ValueCaps.ReportID; } } } _NumValues = 0; for (int i = 0; i < _NumValCaps; i++) //if (Values[i].IsRange) // _NumValues += Values[i].UsageMax - Values[i].Usage + 1; //else _NumValues++; _NumItems = _NumBtnCaps + _NumValues; if (_NumItems > 0) Items = new HID_DATA[_NumItems]; //if ((ButtonCaps != null) && (Items != null)) if ((_NumBtnCaps > 0) && (Items != null)) { for (int i = 0; i < _NumBtnCaps; i++) { Items[i].IsButtonData = 1; Items[i].Status = CyConst.HIDP_STATUS_SUCCESS; Items[i].UsagePage = Buttons[i].UsagePage; if (Buttons[i].IsRange) { Items[i].Usage = Buttons[i].Usage; Items[i].UsageMax = Buttons[i].UsageMax; } else Items[i].Usage = Items[i].UsageMax = Buttons[i].Usage; Items[i].MaxUsageLength = PInvoke.HidP_MaxUsageListLength( rType, Buttons[i].UsagePage, PreparsedDta); Items[i].Usages = new ushort[Items[i].MaxUsageLength]; Items[i].ReportID = Buttons[i].ReportID; } } for (int i = 0; i < _NumValues; i++) { if (Values[i].IsRange) { for (ushort usage = Values[i].Usage; usage <= Values[i].UsageMax; usage++) { Items[i].IsButtonData = 0; Items[i].Status = CyConst.HIDP_STATUS_SUCCESS; Items[i].UsagePage = Values[i].UsagePage; Items[i].Usage = usage; Items[i].ReportID = Values[i].ReportID; } } else { Items[i].IsButtonData = 0; Items[i].Status = CyConst.HIDP_STATUS_SUCCESS; Items[i].UsagePage = Values[i].UsagePage; Items[i].Usage = Values[i].Usage; Items[i].ReportID = Values[i].ReportID; } } }