Mac中如何获取usb设备的设备描述符和配置描述符?
我对 xcode 和 I/Okit 框架的接触最少。我在USB探测器中看到了USB设备的设备描述符和配置描述符。
我编写了一个xcode程序使用 I/O 套件框架,当我们提供该设备的产品 id 和供应商 id 作为输入时,该框架将 USB 设备名称作为输出。
/*Take the vendor and product id from console*/
printf("\nEnter the vendor id : ");
scanf("%lx",&usbVendor);
printf("\nEnter the product id :");
scanf("%lx",&usbProduct);
/* Set up a matching dictionary for the class */
matchingDict = IOServiceMatching(kIOUSBDeviceClassName);
if (matchingDict == NULL)
{
return -1; // fail
}
// Create a CFNumber for the idVendor and set the value in the dictionary
numberRef = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &usbVendor);
CFDictionarySetValue(matchingDict,
CFSTR(kUSBVendorID),
numberRef);
CFRelease(numberRef);
// Create a CFNumber for the idProduct and set the value in the dictionary
numberRef = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &usbProduct);
CFDictionarySetValue(matchingDict,
CFSTR(kUSBProductID),
numberRef);
CFRelease(numberRef);
numberRef = NULL;
/*Get an iterator.*/
kr = IOServiceGetMatchingServices(kIOMasterPortDefault, matchingDict, &iter);
if (kr != KERN_SUCCESS)
{
return -1;// fail
}
/* iterate */
while ((device = IOIteratorNext(iter)))
{
/*Display the device names */
io_name_t deviceName;
kr = IORegistryEntryGetName(device, deviceName);
if (KERN_SUCCESS != kr) {
deviceName[0] = '\0';
}
printf("\ndeviceName:%s",deviceName);
/*Free the reference taken before continuing to the next item */
IOObjectRelease(device);
}
/*Release the iterator */
IOObjectRelease(iter);
return 0;
。
我需要修改它,以便在提供 USB 设备的供应商和产品 ID 时,我将获得设备描述符和配置描述符(如 USB 探测器中所示)作为输出
这里我只是举了一个例子,代码可以改变,但输出必须是描述符(至少是设备描述符)。
提前致谢...
I have minimum exposure to xcode and I/Okit framework. I have seen device descriptor and configuration descriptor of a usb device in USB prober.
I have written an xcode program using I/O kit framework which gives the usb device name as output, when we give product id and vendor id of that device as input.
/*Take the vendor and product id from console*/
printf("\nEnter the vendor id : ");
scanf("%lx",&usbVendor);
printf("\nEnter the product id :");
scanf("%lx",&usbProduct);
/* Set up a matching dictionary for the class */
matchingDict = IOServiceMatching(kIOUSBDeviceClassName);
if (matchingDict == NULL)
{
return -1; // fail
}
// Create a CFNumber for the idVendor and set the value in the dictionary
numberRef = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &usbVendor);
CFDictionarySetValue(matchingDict,
CFSTR(kUSBVendorID),
numberRef);
CFRelease(numberRef);
// Create a CFNumber for the idProduct and set the value in the dictionary
numberRef = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &usbProduct);
CFDictionarySetValue(matchingDict,
CFSTR(kUSBProductID),
numberRef);
CFRelease(numberRef);
numberRef = NULL;
/*Get an iterator.*/
kr = IOServiceGetMatchingServices(kIOMasterPortDefault, matchingDict, &iter);
if (kr != KERN_SUCCESS)
{
return -1;// fail
}
/* iterate */
while ((device = IOIteratorNext(iter)))
{
/*Display the device names */
io_name_t deviceName;
kr = IORegistryEntryGetName(device, deviceName);
if (KERN_SUCCESS != kr) {
deviceName[0] = '\0';
}
printf("\ndeviceName:%s",deviceName);
/*Free the reference taken before continuing to the next item */
IOObjectRelease(device);
}
/*Release the iterator */
IOObjectRelease(iter);
return 0;
}
I need to modify this, so that on giving vendor and product id of usb device, i will get the device descriptor and configuration descriptor( as shown in USB prober) as output.
Here i just gave an example, code can change but the output must be the descriptor( atleast the device decriptor).
Thanks in advance...
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
我认为你应该下载USBProber的源代码而不是自己搞清楚。
USBProber 中提供的所有信息您迟早可以通过分析源代码获得。
这里是下载IOUSBFamily源代码的链接,里面有USBProber。
http://opensource.apple.com/tarballs/IOUSBFamily/
I think u should download the source code of USBProber rather than figure it out by yourself.
All the information presents in the USBProber u could get sooner or later by analyzing the source code.
Here is link to download the source code of IOUSBFamily, with USBProber inside it.
http://opensource.apple.com/tarballs/IOUSBFamily/
要获取配置描述符,您可以使用如下代码:
不幸的是,似乎没有获取设备描述符的函数。有一些函数可以获取其中的一些:
但我没有找到获取
iManufacturer
、iProduct
、iSerial
的方法code>、bMaxPacketSize0
或bcdUSB
。有一种方法可以解决这个问题 - 您可以不使用内置函数,而是使用控制传输手动执行控制请求来获取设备描述符(如果您愿意,还可以获取配置描述符)。
USB 2.0 规范描述了如何执行此操作。基本上,您:
使用 bmRequestType = Device | 进行控制传输标准|在中,
bRequest = USB_GET_DESCRIPTOR_REQUEST
、wValue = (USB_DEVICE_DESCRIPTOR_TYPE << 8)
、wIndex = 0
、wLength = 2 。这会失败,因为描述符长于 2,但它会为您获取包含其长度的描述符标头。
重复该请求,但长度正确。
对于配置描述符,请执行第三个长度为
wTotalLength
的请求。您可以用更少的请求来完成此操作,因为您提前知道描述符的大小,但我喜欢这样做,因为这样您就可以将其包装在一个非常通用的
getDescriptor()
方法中。理论上,您可以像这样简单地执行此操作:
但是由于某种原因,这给了我一个kIOUSBPipeStalled
错误。不知道为什么。编辑:我忘记了
<< 8.
.现在可以了。 :-)To get the configuration descriptors you can use code like this:
Unfortunately there doesn't seem to be a function to get the device descriptor. There are functions to get some of it:
But I don't see a way to get
iManufacturer
,iProduct
,iSerial
,bMaxPacketSize0
, orbcdUSB
.There is a way around this - instead of using the built-in functions you can just do a control request to get the device descriptor (and configuration descriptors if you like) manually using a control transfer.
The USB 2.0 spec describes how to do this. Basically you:
Do a control transfer with
bmRequestType = Device | Standard | In
,bRequest = USB_GET_DESCRIPTOR_REQUEST
,wValue = (USB_DEVICE_DESCRIPTOR_TYPE << 8)
,wIndex = 0
,wLength = 2
. That will fail because the descriptor is longer than 2, but it gets you the descriptor header which includes its length.Repeat that request but with the correct length.
For configuration descriptors, do a third request with length
wTotalLength
.You can do it with one less request since you know the size of the descriptors in advance, but I like to do it like that because then you can wrap it up in a very general
getDescriptor()
method.In theory you can do it as simply as this:
But for some reason that is giving me akIOUSBPipeStalled
error. Not sure why.Edit: I forgot the
<< 8
. Now it works. :-)标头 IOKit/usb/USBSpec.h 具有与不同描述符内的值相对应的属性键的记录列表。您可以将其与 IORegistryEntrySearchCFProperty(或类似函数)一起使用来获取描述符值。这样您就不需要来自 IOUSBDeviceInterface 的设备请求,这是有利的,因为:
The header
IOKit/usb/USBSpec.h
has a documented list of property keys corresponding to values inside the different descriptors. You can use those withIORegistryEntrySearchCFProperty
(or similar functions) to get the descriptor values. This way you don't need a device request from anIOUSBDeviceInterface
, which is advantageous because:为了获取设备描述符和配置描述符,我们可以使用 IOUSBDeviceInterface 类中的函数
链接: http://developer.apple.com/library/mac/#documentation/Darwin/Reference/IOKit/IOUSBLib_h/Classes/IOUSBDeviceInterface/index.html#//apple_ref/doc/com/intfm/IOUSBDeviceInterface /
为了获取接口描述符和端点描述符,我们可以使用IOUSBInterfaceInterface类中的函数
链接:http://developer.apple.com/library /mac/#documentation/Darwin/Reference/IOKit/IOUSBLib_h/Classes/IOUSBInterfaceInterface/
For getting device descriptor and configuration decriptor, we can use functions in IOUSBDeviceInterface class
Link: http://developer.apple.com/library/mac/#documentation/Darwin/Reference/IOKit/IOUSBLib_h/Classes/IOUSBDeviceInterface/index.html#//apple_ref/doc/com/intfm/IOUSBDeviceInterface/
For getting interface descriptor and end point descriptor, we can use functions in IOUSBInterfaceInterface class
Link: http://developer.apple.com/library/mac/#documentation/Darwin/Reference/IOKit/IOUSBLib_h/Classes/IOUSBInterfaceInterface/