利用win32 API和HID设备通信

本文详细介绍了如何利用C++通过win32 API与HID(Human Interface Device)设备进行通信,包括获取设备GUID、设备信息集合、设备接口详情,以及设备的创建和读写操作的正确步骤。

第一步:获取HID设备的GUID
函数:

GUID hid_guid;
//函数输出到GUID类型的变量中
HidD_GetHidGuid(&hid_guid);

typedef struct _GUID {
//就是GUID各组所有的十六进制数字
  DWORD Data1;
  WORD  Data2;
  WORD  Data3;
  BYTE  Data4[8];
} GUID;

第二步:获取设备信息集合

//HDEVINFO 是指向设备信息集合的句柄
WINSETUPAPI HDEVINFO SetupDiGetClassDevsW(
  [in, optional] const GUID *ClassGuid,//GUID
  [in, optional] PCWSTR     Enumerator,//指定设备实例的字符串,可以为NULL
  [in, optional] HWND       hwndParent,//窗口句柄
  [in]           DWORD      Flags//过滤设备信息元素,指明需要什么类型的设备
);

第三步:获取设备接口信息

WINSETUPAPI BOOL SetupDiEnumDeviceInterfaces(
  [in]           HDEVINFO                  DeviceInfoSet,//设备信息集
  [in, optional] PSP_DEVINFO_DATA          DeviceInfoData,//指定一个设备信息
  [in]           const GUID                *InterfaceClassGuid,//GUID
  [in]           DWORD                     MemberIndex,//第一次使用时设置为0,然后循环调用该函数,且此项值递加,直到此函数返回值为ERROR_NO_MORE_ITEMS
  [out]          PSP_DEVICE_INTERFACE_DATA DeviceInterfaceData//输出的设备接口信息,在使用此函数之前,
 															 //必须给该结构的cbSize变量赋值为sizeof(SP_DEVICE_INTERFACE_DATA)
);

typedef struct _SP_DEVICE_INTERFACE_DATA {
  DWORD     cbSize;//结构体大小
  GUID      InterfaceClassGuid;//GUID
  DWORD     Flags;//指明该接口是活跃状态还是被移除还是设备类的默认接口
  ULONG_PTR Reserved;
} SP_DEVICE_INTERFACE_DATA, *PSP_DEVICE_INTERFACE_DATA;

第四步:获取设备接口详细信息

WINSETUPAPI BOOL SetupDiGetDeviceInterfaceDetailW(
  [in]            HDEVINFO                           DeviceInfoSet,//设备信息集
  [in]            PSP_DEVICE_INTERFACE_DATA          DeviceInterfaceData,//设备接口信息
  [out, optional] PSP_DEVICE_INTERFACE_DETAIL_DATA_W DeviceInterfaceDetailData,//设备接口详细信息,使用此内容之前,必须使DeviceInterfaceDetailData.cbSize 内容是sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA) 
  [in]            DWORD                              DeviceInterfaceDetailDataSize,//设备接口详细信息大小
  [out, optional] PDWORD                             RequiredSize,//固定长度大小加上设备路径大小
  [out, optional] PSP_DEVINFO_DATA                   DeviceInfoData
);

typedef struct _SP_DEVICE_INTERFACE_DETAIL_DATA_A {
  DWORD cbSize;
  CHAR  DevicePath[ANYSIZE_ARRAY];
} SP_DEVICE_INTERFACE_DETAIL_DATA_A, *PSP_DEVICE_INTERFACE_DETAIL_DATA_A;

正确使用方法:

//先调用一次函数获取RequiredSize的值
SetupDiGetDeviceInterfaceDetail(device_info, &device_interface_data,
			NULL, 0, &requiredSize, NULL);

//先给DeviceInterfaceDetailData的变量分配内存
DeviceInterfaceDetailData p_device_interface_detail_data ;
p_device_interface_detail_data = (PSP_DEVICE_INTERFACE_DETAIL_DATA)malloc(requiredSize);
p_device_interface_detail_data->cbSize = sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA);
//再调用一次获取设备接口的详细信息
isGetDeviceInterfaceDetail = SetupDiGetDeviceInterfaceDetail(
	device_info,
	&device_interface_data,
	p_device_interface_detail_data,
	requiredSize,
	NULL,
	NULL);

第五步:创建设备

函数返回
HANDLE CreateFileA(
  [in]           LPCSTR                lpFileName,//设备路径
  [in]           DWORD                 dwDesiredAccess,// 对设备或者文件的访问权限GENERIC_READ, GENERIC_WRITE
  [in]           DWORD                 dwShareMode,//设置共享模式,可以设置为FILE_SHARE_READ ,FILE_SHARE_WRITE
  [in, optional] LPSECURITY_ATTRIBUTES lpSecurityAttributes,//安全属性,是一个结构体,可以置为NULL
  [in]           DWORD                 dwCreationDisposition,//对存在或不存在文件处理方法,对于设备常设置为OPEN_EXISTING
  [in]           DWORD                 dwFlagsAndAttributes,//常设置为FILE_ATTRIBUTE_NORMAL 
  [in, optional] HANDLE                hTemplateFile//可以置为NULL
);

第六步:读写

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值