public static Collection <DeviceInformation> GetConnectedDeviceInformations() { var deviceInformations = new Collection <DeviceInformation>(); var spDeviceInterfaceData = new SpDeviceInterfaceData(); var spDeviceInfoData = new SpDeviceInfoData(); var spDeviceInterfaceDetailData = new SpDeviceInterfaceDetailData(); spDeviceInterfaceData.CbSize = (uint)Marshal.SizeOf(spDeviceInterfaceData); spDeviceInfoData.CbSize = (uint)Marshal.SizeOf(spDeviceInfoData); var hidGuid = new Guid(); APICalls.HidD_GetHidGuid(ref hidGuid); var i = APICalls.SetupDiGetClassDevs(ref hidGuid, IntPtr.Zero, IntPtr.Zero, APICalls.DigcfDeviceinterface | APICalls.DigcfPresent); if (IntPtr.Size == 8) { spDeviceInterfaceDetailData.CbSize = 8; } else { spDeviceInterfaceDetailData.CbSize = 4 + Marshal.SystemDefaultCharSize; } var x = -1; while (true) { x++; var setupDiEnumDeviceInterfacesResult = APICalls.SetupDiEnumDeviceInterfaces(i, IntPtr.Zero, ref hidGuid, (uint)x, ref spDeviceInterfaceData); var errorNumber = Marshal.GetLastWin32Error(); //TODO: deal with error numbers. Give a meaningful error message if (setupDiEnumDeviceInterfacesResult == false) { break; } APICalls.SetupDiGetDeviceInterfaceDetail(i, ref spDeviceInterfaceData, ref spDeviceInterfaceDetailData, 256, out _, ref spDeviceInfoData); var deviceInformation = GetDeviceInformation(spDeviceInterfaceDetailData.DevicePath); if (deviceInformation == null) { continue; } deviceInformations.Add(deviceInformation); } APICalls.SetupDiDestroyDeviceInfoList(i); return(deviceInformations); }
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); }
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); } }