【问题标题】:What do I pass as the last value to the function SetupAPI.DLL.SetupDiEnumDeviceInterfaces()?我将什么作为最后一个值传递给函数 SetupAPI.DLL.SetupDiEnumDeviceInterfaces()?
【发布时间】:2026-02-24 03:15:01
【问题描述】:

我正在使用 Python 尝试创建一个简单的程序,该程序可以从一个相当简单的 USB 设备读取和写入数据。我遇到的问题是,由于 PyWinUSB 和 PyUSB 似乎没有我需要的东西(尝试写入设备会使事情爆炸),我必须使用 ctypes python 模块和原始 dll 函数从头开始工作WinUSB 和 SetupAPI。

我已经能够回答关于如何定义我传递给函数的结构的问题,但我现在遇到的问题是根据函数的规范......好吧, 我只是引用它。

"DeviceInterfaceData [out]

A pointer to a caller-allocated buffer that contains, on successful return, a
completed SP_DEVICE_INTERFACE_DATA structure that identifies an interface that meets
the search parameters. The caller must set DeviceInterfaceData.cbSize to
sizeof(SP_DEVICE_INTERFACE_DATA) before calling this function."

如何将这些要求转换为 Python?

我现在使用的结构类如下所示:

class _SP_DEVINFO_DATA(ctypes.Structure):
    _fields_ = [("cbSize", wintypes.DWORD),
                ("ClassGuid", (ctypes.c_char * 16)),
                ("DevInst", wintypes.DWORD),
                ("Reserved", wintypes.LPVOID)]

    def __init__(self, guid, inst):
        self.cbSize = ctypes.sizeof(self)
        self.ClassGuid = uuid.UUID(guid).get_bytes()
        self.DevInst = (wintypes.DWORD)(inst)
        self.Reserved = None

    def __repr__(self):
        return "_SP_DEV_INFO_DATA(cbsize={}, ClassGuid={}, DevInst={})".format(
            self.cbSize, uuid.UUID(bytes=self.ClassGuid), hex(self.DevInst))

根据之前问题的答案告诉我。

谢谢。

【问题讨论】:

    标签: python-2.7 ctypes windows-7-x64 setupapi pywinusb


    【解决方案1】:

    SP_DEVINFO_DATA 结构由SetupDiEnumDeviceInfo返回SetupDiEnumDeviceInterfaces 有不同的结构。在这两种情况下,您都需要构造结构,仅初始化 cbSize 参数,然后通过引用将其传递给函数:

    示例(未经测试,仅凭记忆输入):

    class SP_DEVICE_INTERFACE_DATA(ctypes.Structure):
        _fields_ = [('cbSize',wintypes.DWORD),
                    ('InterfaceClassGuid',ctypes.c_char*16),
                    ('Flags',wintypes.DWORD),
                    ('Reserved',wintypes.LPVOID)]
        def __init__(self):
            self.cbSize = ctypes.sizeof(self)
    
    PSP_DEVICE_INTERFACE_DATA = ctypes.POINTER(SP_DEVICE_INTERFACE_DATA)
    
    i = 0
    idata = SP_DEVICE_INTERFACE_DATA()
    
    while True:
        if not SetupDiEnumDeviceInterfaces(handle,None,guid,i,ctypes.byref(idata)):
            break
        <do something with idata>
        i += 1
    

    【讨论】:

    • 如果不是 SetupDIEnumDeviceInterfaces(),当该函数失败时返回 0 时,它不会是 True 吗?我尝试运行this,并在键盘中断之前进行了超过 1000 次迭代,而我定义的对象中没有出现任何内容。再次感谢。
    • 无法查看您的代码。说是私人贴。是的,当函数失败时,if 为真并从循环中中断。您忘记增加索引了吗?
    • 抱歉,再看一遍。我确实记得增加索引,但问题是函数每次都失败。
    • DIGCF_DEVICEINTERFACE 不是字符串,它是一个值为 0x10 的常量。您必须在 windows 头文件中查找该值。另外,您必须先致电SetupDiEnumDeviceInfoSetupDiEnumDeviceInterfacesSP_DEVINFO_DATA 指针作为其第二个参数,您将其设置为 None。 this 是你想要做什么?
    • 我刚刚意识到,我可以看看 PyWinUSB 模块,看看他们在那里做了什么,以及如何根据我的需要调整它。我不敢相信我花了这么长时间才意识到这一点。我只是想停下来再次感谢您给我的所有帮助,如果我还有其他问题,我一定会回来的。再次感谢。
    最近更新 更多