文章目录
- 接口介绍
- 概述
- 过滤器
- 介绍
- 举例
- 接收通知
- 创建窗口
- 参考文档
接口介绍
概述
-
window提供了
RegisterDeviceNotificationW
方法,可以用来监听设备的热插拔事件。HDEVNOTIFY RegisterDeviceNotificationW( [in] HANDLE hRecipient, [in] LPVOID NotificationFilter, [in] DWORD Flags );
- hRecipient,表示用来接收通知的窗口或者服务。
- NotificationFilter,过滤器,用来过滤设备通知。
- Flags,用来说明
hRecipient
是个窗口还是服务。 - 通知必须绑定到窗口或者服务,也就是说在监听之前,你必须先创建一个窗口或者服务。
过滤器
介绍
NotificationFilter
其基本结构为DEV_BROADCAST_HDR,具体结构根据dbch_devicetype
字段值的不同而不同,typedef struct _DEV_BROADCAST_HDR { DWORD dbch_size; DWORD dbch_devicetype; DWORD dbch_reserved; } DEV_BROADCAST_HDR;
dbch_devicetype
字段可能的值如下:
举例
- 我们以
dbch_devicetype
的值是DBT_DEVTYP_DEVICEINTERFACE
为例,其对应的NotificationFilter
是DEV_BROADCAST_DEVICEINTERFACE_A,如下:typedef struct _DEV_BROADCAST_DEVICEINTERFACE_A { DWORD dbcc_size; DWORD dbcc_devicetype; DWORD dbcc_reserved; GUID dbcc_classguid; char dbcc_name[1]; } DEV_BROADCAST_DEVICEINTERFACE_A;
dbcc_classguid
这个是GUID用来表示我们所关注的事件。那么什么是GUID?其全称为globally unique identifier
,就像它的名字一样,GUID是一个系统级全局的唯一标识符。- USB相关的GUID有如下一些:
GUID_DEVINTERFACE_USB_DEVICE
表示连接到HUB的USB设备。GUID_DEVINTERFACE_USB_HOST_CONTROLLER
表示USB主机控制器。GUID_DEVINTERFACE_USB_HUB
表示USB HUB。
接收通知
- 上面都是在说如何监听热插拔通知,那么我们监听好了之后,到底怎么样接收插拔通知,以及如何解析这些通知呢?
- 上面我们说了,监听通知时必须绑定到窗口或者服务。也就是和
RegisterDeviceNotificationW
这个接口的hRecipient
参数有关系。所以我们需要了解一些窗口相关的知识。
创建窗口
- 首先我们需要通过接口
RegisterClassA
创建一个类。该接口包含如下参数:typedef struct tagWNDCLASSA { UINT style; WNDPROC lpfnWndProc; int cbClsExtra; int cbWndExtra; HINSTANCE hInstance; HICON hIcon; HCURSOR hCursor; HBRUSH hbrBackground; LPCSTR lpszMenuName; LPCSTR lpszClassName; } WNDCLASSA, *PWNDCLASSA, *NPWNDCLASSA, *LPWNDCLASSA;
lpfnWndProc
,这个参数是窗口的回调函数。也就是是说如果有通知消息发给窗口,那么就会调用该回调来处理。也就是说我们上面订阅的通知会被发送给该函数处理。hInstance
,该窗口所属的实例。lpszClassName
, 窗口类名,这个很重要。我们创建好这个类之后,后面才能基于这个类创建窗口。
- 接着我们就可以通过
CreateWindowEx
接口创建一个窗口,该接口会返回一个HWND
,可用于上面注册设备通知的接口。
参考文档
- RegisterDeviceNotificationW function (winuser.h)
- Windows监听USB热插拔事件
- 硬件检测:安装、停用
- GUID structure (guiddef.h)
- GUIDs
- GUID_DEVINTERFACE_USB_DEVICE