The usbview sample application in WinDDK (src/usb/usbview) shows how
to find the physical location of devices, however, we can't find any
way to actually get a HANDLE to the device, or find it's DevicePath
that we could use to call CreateFile. Once usbview has a handle to a
hub, it uses DevicIoControl with
IOCTL_USB_GET_NODE_CONNECTION_INFORMATION_EX to get the information
about the usb device connected to the port, without actually opening a
connection to it. We can't find a way to use this information to get
a HANDLE to the device.
The hclient sample application (src/hid/hclient) shows how to read
from HID joysticks, but the enumeration uses SetupDi* functions where
the order of devices is independent of physical location. We would
need a DevicePath to call OpenHidDevice().
Is there any way for us to sync up the enumeration as done in hclient
with the enumeration done in usbview? Does anyone know how we can get
a DevicePath of a device found in usbview, or a HANDLE to it?
For the following calls you'll need device instance IDs which you would
probably get from cfgmgr32 calls like the above.
AFAIK you can't get "the child device on port N", but you can check a
child device's port number given it's device instance ID:
SetupDiGetClassDevs*
SetupDiEnumDeviceInfo
SetupDiGetDeviceProperty <-- get the device's Address; this is
documented under Address/USB here:
http://msdn.microsoft.com/en-us/library/dd852021.aspx
Getting a handle to the device:
SetupDiGetClassDevs*
SetupDiEnumDeviceInterfaces <-- you need to know a device interface GUID
for the device, in your case should be something related to joysticks/input
SetupDiGetDeviceInterfaceDetail
That will give you the device path for CreateFile.
* You can call SetupDiGetClassDevs just once across both of the above
tasks for 1 device. Note you have to call SetupDiDestroyDeviceInfoList
when you're done.
Philip