Ctypes如何解析SetupDiGetDeviceRegistryPropertyW返回的缓冲区
问题原因
打印得到指针对象是因为直接输出了ctypes指针实例本身,没有读取指针指向的内存内容,同时代码存在几处逻辑错误会导致解析失败:
- 仅定义了ANSI版本
SetupDiGetDeviceRegistryPropertyA的参数约束,未定义Wide版本SetupDiGetDeviceRegistryPropertyW的argtypes/restype,ctypes会按默认规则传参,容易触发内存访问异常 - 传入
PropertyRegDataType参数时传了None,该参数要求传入DWORD指针接收注册表值类型,传空会导致函数调用不符合API约定 SPDRP_HARDWAREID对应的注册表值类型是REG_MULTI_SZ(多字符串格式),内容是多个以\0分隔的硬件ID字符串,末尾以双\0结尾,不是单个WCHAR字符串,直接转单WCHAR指针无法正确读取全部内容POINTER(w.WCHAR)是指向单个宽字符的指针类型,直接打印该类型变量只会输出对象的内存地址表示,不会自动解引用读取连续的字符串内容
正确修复方法
第一步:补全W版本API的参数定义
在原有API定义部分补充以下代码:
SetupAPI.SetupDiGetDeviceRegistryPropertyW.argtypes = HDEVINFO, PSP_DEVINFO_DATA, w.DWORD, w.PDWORD, w.PBYTE, w.DWORD, w.PDWORD SetupAPI.SetupDiGetDeviceRegistryPropertyW.restype = w.BOOL
第二步:修正参数传递与缓冲区解析逻辑
替换原循环内的属性读取、解析代码:
PropertyRegDataType = w.DWORD() # 原代码传None为错误写法 # 第一次调用获取所需缓冲区大小 SetupAPI.SetupDiGetDeviceRegistryPropertyW( hDevInfo, ct.byref(devinfo), SPDRP_HARDWAREID, ct.byref(PropertyRegDataType), None, PropertyBufferSize , ct.byref(RequiredSize)) PropertyBuffer = (w.BYTE * RequiredSize.value)() if not SetupAPI.SetupDiGetDeviceRegistryPropertyW( hDevInfo, ct.byref(devinfo), SPDRP_HARDWAREID, ct.byref(PropertyRegDataType), PropertyBuffer, ct.sizeof(PropertyBuffer), None): MemberIndex += 1 continue # 解析REG_MULTI_SZ格式内容,直接转字节按UTF-16LE解码最稳妥 raw_content = bytes(PropertyBuffer).decode('utf-16-le') hardware_id_list = [item for item in raw_content.split('\0') if item] print("当前设备硬件ID列表:", hardware_id_list) # 从硬件ID中提取VID/PID for id_str in hardware_id_list: if id_str.startswith('USB\\VID_') and '&PID_' in id_str: vid = id_str.split('VID_')[1][:4] pid = id_str.split('PID_')[1][:4] print(f"厂商ID: 0x{vid.upper()}, 产品ID: 0x{pid.upper()}")
补充:单字符串属性的正确读取方式
如果读取的是SPDRP_FRIENDLYNAME、SPDRP_DEVICEDESC这类REG_SZ类型的单字符串属性,cast指针后取.value即可拿到完整Python字符串:
str_ptr = ct.cast(PropertyBuffer, w.LPWSTR) device_name = str_ptr.value print(device_name)
不要直接用
ct.POINTER(w.WCHAR)转换字符串缓冲区,该类型是指向单个WCHAR的指针,没有自动读取连续字符串的能力,用w.LPWSTR(ctypes预定义的宽字符串指针)的value属性,才会自动读取到\0终止符位置的完整字符串。
内容的提问来源于stack exchange,提问作者user19212551
相关产品推荐
相关产品推荐

