0

I need to connect to a USB-device connected to the computer, I have looked around a bit and found some example projects, but cant get this to work. Everything runs nice, but I don't even get into the while-function. Since SetupDiGetClassDevs is from the setupapi.dll I can't debug this function. I do have devices connected, so that is not my problem. Also hInfoSet does get size = 8.

public static HIDDevice FindDevice(int nVid, int nPid, Type oType)
{
 string strPath = string.Empty;
 string strSearch = string.Format("vid_{0:x4}&pid_{1:x4}", nVid, nPid); // first, build the path search string
 Guid gHid;
 HidD_GetHidGuid(out gHid); // next, get the GUID from Windows that it uses to represent the HID USB interface
 IntPtr hInfoSet = SetupDiGetClassDevs(ref gHid, null, IntPtr.Zero, DIGCF_DEVICEINTERFACE | DIGCF_PRESENT); // this gets a list of all HID devices currently connected to the computer (InfoSet)
 try
 {
 DeviceInterfaceData oInterface = new DeviceInterfaceData(); // build up a device interface data block
 oInterface.Size = Marshal.SizeOf(oInterface);
 // Now iterate through the InfoSet memory block assigned within Windows in the call to SetupDiGetClassDevs
 // to get device details for each device connected
 int nIndex = 0;
 while (SetupDiEnumDeviceInterfaces(hInfoSet, 0, ref gHid, (uint)nIndex, ref oInterface)) // this gets the device interface information for a device at index 'nIndex' in the memory block
 {
 string strDevicePath = GetDevicePath(hInfoSet, ref oInterface); // get the device path (see helper method 'GetDevicePath')
 if (strDevicePath.IndexOf(strSearch) >= 0) // do a string search, if we find the VID/PID string then we found our device!
 {
 HIDDevice oNewDevice = (HIDDevice)Activator.CreateInstance(oType); // create an instance of the class for this device
 oNewDevice.Initialise(strDevicePath); // initialise it with the device path
 return oNewDevice; // and return it
 }
 nIndex++; // if we get here, we didn't find our device. So move on to the next one.
 }
 }
 finally
 {
 // Before we go, we have to free up the InfoSet memory reserved by SetupDiGetClassDevs
 SetupDiDestroyDeviceInfoList(hInfoSet);
 }
 return null; 
}
BenMorel
37k52 gold badges208 silver badges339 bronze badges
asked Nov 19, 2013 at 10:39

1 Answer 1

1

Have you tried calling Marshal.GetLastWin32Error and printing the value after the while loop if it's not entering? Make sure to enable SetLastError on SetupDiEnumDeviceInterfaces.

Afterwards, lookup your error code here: http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381%28v=vs.85%29.aspx

EDIT - After reading your comment, the structure should look something like this:

[StructLayout(LayoutKind.Sequential)]
struct GUID
{
 public int a;
 public short b;
 public short c;
 [MarshalAs(UnmanagedType.ByValArray, SizeConst=8)]
 public byte[] d;
}
[StructLayout(LayoutKind.Sequential)]
struct SP_DEVICE_INTERFACE_DATA
{
 public uint cbSize;
 public GUID InterfaceClassGuid;
 public uint Flags;
 public IntPtr Reserved;
}
answered Nov 19, 2013 at 11:16
Sign up to request clarification or add additional context in comments.

2 Comments

Thanks! I tryed this now, and got "1784: The supplied user buffer is not valid for the requested operation". But I'm still not sure how to fix this, do you have any idea why this error occures?
My guess is that your "DeviceInterfaceData" structure is not marshalled correctly (Marshal.SizeOf is returning the wrong size). Check my edited post.

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.