public bool Initialize() { Dispose(); if (DeviceInformation == null) { throw new WindowsHidException($"{nameof(DeviceInformation)} must be specified before {nameof(Initialize)} can be called."); } var pointerToPreParsedData = new IntPtr(); _HidCollectionCapabilities = new HidCollectionCapabilities(); var pointerToBuffer = Marshal.AllocHGlobal(126); _ReadSafeFileHandle = APICalls.CreateFile(DeviceInformation.DevicePath, APICalls.GenericRead | APICalls.GenericWrite, APICalls.FileShareRead | APICalls.FileShareWrite, IntPtr.Zero, APICalls.OpenExisting, 0, IntPtr.Zero); _WriteSafeFileHandle = APICalls.CreateFile(DeviceInformation.DevicePath, APICalls.GenericRead | APICalls.GenericWrite, APICalls.FileShareRead | APICalls.FileShareWrite, IntPtr.Zero, APICalls.OpenExisting, 0, IntPtr.Zero); if (!APICalls.HidD_GetPreparsedData(_ReadSafeFileHandle, ref pointerToPreParsedData)) { throw new Exception("Could not get pre parsed data"); } var getCapsResult = APICalls.HidP_GetCaps(pointerToPreParsedData, ref _HidCollectionCapabilities); //TODO: Deal with issues here Marshal.FreeHGlobal(pointerToBuffer); var preparsedDataResult = APICalls.HidD_FreePreparsedData(ref pointerToPreParsedData); //TODO: Deal with issues here if (_ReadSafeFileHandle.IsInvalid) { return(false); } _ReadFileStream = new FileStream(_ReadSafeFileHandle, FileAccess.ReadWrite, _HidCollectionCapabilities.OutputReportByteLength, false); _WriteFileStream = new FileStream(_WriteSafeFileHandle, FileAccess.ReadWrite, _HidCollectionCapabilities.InputReportByteLength, false); IsInitialized = true; Connected?.Invoke(this, new EventArgs()); return(true); }
internal static extern int HidP_GetCaps(IntPtr pointerToPreparsedData, ref HidCollectionCapabilities hidCollectionCapabilities);
private static DeviceInformation GetDeviceInformation(string devicePath) { using (var safeFileHandle = APICalls.CreateFile(devicePath, APICalls.GenericRead | APICalls.GenericWrite, APICalls.FileShareRead | APICalls.FileShareWrite, IntPtr.Zero, APICalls.OpenExisting, 0, IntPtr.Zero)) { var hidCollectionCapabilities = new HidCollectionCapabilities(); var hidAttributes = new HidAttributes(); var pointerToPreParsedData = new IntPtr(); var product = string.Empty; var serialNumber = string.Empty; var manufacturer = string.Empty; var pointerToBuffer = Marshal.AllocHGlobal(126); var preparsedDataResult = APICalls.HidD_GetPreparsedData(safeFileHandle, ref pointerToPreParsedData); if (!preparsedDataResult) { return(null); } //TODO: Deal with issues here var getCapsResult = APICalls.HidP_GetCaps(pointerToPreParsedData, ref hidCollectionCapabilities); //TODO: Deal with issues here if (!APICalls.HidD_GetAttributes(safeFileHandle, ref hidAttributes)) { throw new Exception("Could not obtain attributes"); } if (APICalls.HidD_GetManufacturerString(safeFileHandle, pointerToBuffer, 126)) { manufacturer = Marshal.PtrToStringUni(pointerToBuffer); } if (APICalls.HidD_GetSerialNumberString(safeFileHandle, pointerToBuffer, 126)) { serialNumber = Marshal.PtrToStringUni(pointerToBuffer); } if (APICalls.HidD_GetProductString(safeFileHandle, pointerToBuffer, 126)) { product = Marshal.PtrToStringUni(pointerToBuffer); } Marshal.FreeHGlobal(pointerToBuffer); var getPreparsedDataResult = APICalls.HidD_FreePreparsedData(ref pointerToPreParsedData); //TODO: Deal with issues here var deviceInformation = new DeviceInformation { DevicePath = devicePath, InputReportByteLength = hidCollectionCapabilities.InputReportByteLength, Manufacturer = manufacturer, OutputReportByteLength = hidCollectionCapabilities.OutputReportByteLength, Product = product, ProductId = (ushort)hidAttributes.ProductId, SerialNumber = serialNumber, Usage = hidCollectionCapabilities.Usage, UsagePage = hidCollectionCapabilities.UsagePage, VendorId = (ushort)hidAttributes.VendorId, VersionNumber = (ushort)hidAttributes.VersionNumber }; return(deviceInformation); } }