返回

python-Ctypes-如何解析缓冲区内容?

发布时间:2022-07-07 03:37:28 177
# node.js

我有代码使用SetupDiGetDeviceRegistryPropertyW为了枚举USB供应商id和产品id,我从缓冲区读取为,如何解析?

缓冲器

result = ct.cast(PropertyBuffer,ct.POINTER(w.WCHAR))

密码

import ctypes as ct
from ctypes import wintypes as w
import uuid

SetupAPI = ct.WinDLL('SetupAPI')

ULONG_PTR = w.WPARAM

class HDEVINFO(w.HANDLE):
    pass

class GUID(ct.Structure):
    _fields_ = (('Data1', ct.c_ulong),
                ('Data2', ct.c_ushort),
                ('Data3', ct.c_ushort),
                ('Data4', ct.c_ubyte * 8))

    def __repr__(self):
        return f"GUID('{self}')"

    def __str__(self):
        return (f'{{{self.Data1:08x}-{self.Data2:04x}-{self.Data3:04x}-'
                f'{bytes(self.Data4[:2]).hex()}-{bytes(self.Data4[2:]).hex()}}}')

    def __init__(self,guid=None):
        if guid is not None:
            data = uuid.UUID(guid)
            self.Data1 = data.time_low
            self.Data2 = data.time_mid
            self.Data3 = data.time_hi_version
            self.Data4[0] = data.clock_seq_hi_variant
            self.Data4[1] = data.clock_seq_low
            self.Data4[2:] = data.node.to_bytes(6,'big')

PGUID = ct.POINTER(GUID)

GUID_DEVINTERFACE_USB_DEVICE = GUID('{A5DCBF10-6530-11D2-901F-00C04FB951ED}')

class SP_DEVINFO_DATA(ct.Structure):

    _fields_ = (('cbSize', w.DWORD), 
                ('ClassGuid', GUID), 
                ('DevInst', w.DWORD), 
                ('Reserved', ULONG_PTR))

    def __repr__(self):
        return f'SP_DEVINFO_DATA(ClassGuid={self.ClassGuid}, DevInst={self.DevInst})'

    def __init__(self):
        self.cbSize = ct.sizeof(SP_DEVINFO_DATA)      

PSP_DEVINFO_DATA = ct.POINTER(SP_DEVINFO_DATA)

SetupAPI.SetupDiGetClassDevsW.argtypes = PGUID, w.PWCHAR, w.HWND, w.DWORD
SetupAPI.SetupDiGetClassDevsW.restype = HDEVINFO

SetupAPI.SetupDiEnumDeviceInfo.argtypes = HDEVINFO, w.DWORD, PSP_DEVINFO_DATA
SetupAPI.SetupDiEnumDeviceInfo.restype = w.BOOL 

SetupAPI.SetupDiGetDeviceRegistryPropertyA.argtypes = HDEVINFO, PSP_DEVINFO_DATA, 
w.DWORD, w.PDWORD, w.PBYTE, w.DWORD, w.PDWORD
SetupAPI.SetupDiGetDeviceRegistryPropertyA.restype = w.BOOL

SetupAPI.SetupDiDestroyDeviceInfoList.argtypes = HDEVINFO,
SetupAPI.SetupDiDestroyDeviceInfoList.restype = w.BOOL

DIGCF_DEFAULT         =  0x00000001  
DIGCF_PRESENT         =  0x00000002
DIGCF_ALLCLASSES      =  0x00000004
DIGCF_PROFILE         =  0x00000008
DIGCF_DEVICEINTERFACE =  0x00000010

ClassGuid = GUID_DEVINTERFACE_USB_DEVICE
Enumerator = None
hwndParent = None
Flags = DIGCF_DEVICEINTERFACE | DIGCF_PRESENT

devinfo = SP_DEVINFO_DATA()

hDevInfo = SetupAPI.SetupDiGetClassDevsW(ClassGuid, Enumerator, hwndParent, Flags)


DeviceInfoSet = hDevInfo
DeviceInfoData = ct.byref(devinfo)    
SPDRP_HARDWAREID = 0x00000001
PropertyRegDataType = None
PropertyBufferSize = 0
RequiredSize = w.DWORD()

try:
    MemberIndex = 0
    while SetupAPI.SetupDiEnumDeviceInfo(hDevInfo, MemberIndex, ct.byref(devinfo)):       
        print(devinfo)          
        SetupAPI.SetupDiGetDeviceRegistryPropertyW(
                                               hDevInfo,
                                               ct.byref(devinfo),
                                               SPDRP_HARDWAREID,
                                               PropertyRegDataType,
                                               None, 
                                               PropertyBufferSize ,
                                               ct.byref(RequiredSize))
    
        PropertyBuffer = (w.BYTE * RequiredSize.value)()
        if not SetupAPI.SetupDiGetDeviceRegistryPropertyW(
                                                     hDevInfo,
                                                     ct.byref(devinfo),
                                                     SPDRP_HARDWAREID,
                                                     PropertyRegDataType,
                                                     PropertyBuffer, 
                                                     ct.sizeof(PropertyBuffer),
                                                     None):
           break
        result = ct.cast(PropertyBuffer,ct.POINTER(w.WCHAR))
        print(result)
        MemberIndex += 1            
           
finally:
    SetupAPI.SetupDiDestroyDeviceInfoList(hDevInfo)
特别声明:以上内容(图片及文字)均为互联网收集或者用户上传发布,本站仅提供信息存储服务!如有侵权或有涉及法律问题请联系我们。
举报
评论区(1)
按点赞数排序
用户头像