问题描述
在我目前正在处理的项目中,我必须通过 VID 和 PID 来定位 USB 设备(即查找设备的总线和端口号)。 我无法修改与此设备配合使用的大量代码,因此我无法使用其他方法传递该设备。
我发现可以在我的环境(C++、Boost、Qt、Linux)中实现的这个问题的最简单解决方案之一是使用 libusb。阅读文档和查看示例后,我想出了以下代码:
std::pair<uint8_t,uint8_t> get_usb_address(uint16_t vid,uint16_t pid)
{
libusb_context *context = nullptr;
libusb_device **list = nullptr;
int lib_err = 0; ssize_t devices_count = 0;
lib_err = libusb_init(&context);
if (lib_err != 0)
throw std::runtime_error("getting devices list: unable to init libusb");
devices_count = libusb_get_device_list(context,&list);
if (devices_count <= 0)
throw std::runtime_error("getting devices list: no USB devices found ??");
for (size_t i = 0; i < devices_count; ++i)
{
libusb_device *device = list[i];
libusb_device_descriptor desc = {0};
lib_err = libusb_get_device_descriptor(device,&desc);
if (lib_err != 0)
throw std::runtime_error("getting devices list: unable to get device descriptor");
if ((desc.idvendor == vid ) && (desc.idProduct == pid))
{
uint8_t bus_num = libusb_get_bus_number(device);
uint8_t device_num = libusb_get_port_number(device);
std::cout << "Found device with VID:PID " << std::hex << vid << ":" << pid;
std::cout << " at bus " << bus_num << ",device " << device_num << std::endl;
libusb_free_device_list(list,devices_count);
libusb_exit(context);
return std::make_pair(bus_num,device_num);
}
}
std::cout << "Device not found: VID:PID " << std::hex << vid << ":" << pid << std::endl;
libusb_free_device_list(list,devices_count);
libusb_exit(context);
return std::make_pair(0,0);
}
问题是 libusb_get_bus_number()
和 libusb_get_port_number()
调用总是返回 NULL
,即使设备描述符不为空并且其 idvendor
和 idProduct
字段是有效的(也就是说,这段代码通过 VID/PID 成功匹配了设备,但无法获取其总线地址)。我尝试在几台不同的 Linux 机器上运行此代码,结果相同。
此时,我完全不知所措。 libusb 官方文档甚至没有提到 libusb_get_bus_number()
返回 NULL
的可能性。该问题在不同的机器和 Linux 发行版上仍然存在,因此应该与硬件无关。
任何帮助将不胜感激。
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)