如何解决从WM_DEVICECHANGE LParam
因此,我正在为学校PC构建一个可跟踪所有插入设备的应用程序。
每当插入或移除设备时,我都设法使用RegisterDeviceNotification()
在主线程中获得通知。
我所能得到的只是LParam
,这是设备唯一的指针。
我找不到有关如何使用该LParam获取设备的友好名称的任何信息。 我可以找到的唯一资源是2006年的this CodeProject(使用C ++)。
我在pinvoke.net上找不到任何内容,我发现的唯一内容(我不记得确切的位置)是使用ManagementObjectSearcher
来获取此数据,但它会找到空数据。 (这是代码)
ManagementObjectSearcher searcher = new ManagementObjectSearcher("Select Name from Win32_PnpEntity");
foreach (ManagementObject devices in searcher.Get())
{
foreach (var v in devices.Properties)
{
Console.WriteLine(v.Value);
}
}
searcher.dispose();
有人可以帮我弄清楚如何获得设备的友好名称吗?
解决方法
-
您需要在以下位置注册设备通知
RegisterDeviceNotificationW
static DEV_BROADCAST_DEVICEINTERFACE dbd = { sizeof(dbd),DBT_DEVTYP_DEVICEINTERFACE }; _hDevNot = RegisterDeviceNotificationW(hwnd,&dbd,DEVICE_NOTIFY_WINDOW_HANDLE|DEVICE_NOTIFY_ALL_INTERFACE_CLASSES);
-
结果您将收到
WM_DEVICECHANGE
消息 -
在这里,您需要检查 wParam 中的
DBT_DEVICEARRIVAL
和DBT_DEVICEREMOVECOMPLETE
个事件 -
检查
dbcc_devicetype == DBT_DEVTYP_DEVICEINTERFACE
在 -
设备接口名称
-
您可以在
CM_Get_Device_Interface_PropertyW
中使用此名称 与DEVPKEY_Device_InstanceId
一起使用DBT_DEVICEARRIVAL
事件 - 中使用它
-
在调用
CM_Get_DevNode_PropertyW
中使用result与DEVPKEY_NAME
或DEVPKEY_DeviceInterface_FriendlyName
-
-您只能自我观察 这样的名称和友好的数据库(如果在到达时创建数据库) 名称。
DEV_BROADCAST_DEVICEINTERFACE_W.dbcc_name
内部的DBT_DEVICEREMOVECOMPLETE
上的演示代码:
struct DeviceName : public LIST_ENTRY
{
ULONG InterfaceHash;
WCHAR Name[];
void* operator new(size_t cb,size_t len)
{
return LocalAlloc(0,cb + len);
}
void operator delete(void* pv)
{
LocalFree(pv);
}
};
volatile const UCHAR guz = 0;
CONFIGRET GetFriendlyNameByDevNode(DeviceName** pp,DEVINST dnDevInst)
{
CONFIGRET status;
ULONG cb = 32;
DEVPROPTYPE PropertyType;
do
{
if (DeviceName* p = new(cb) DeviceName)
{
status = CM_Get_DevNode_PropertyW(
dnDevInst,&DEVPKEY_DeviceInterface_FriendlyName,&PropertyType,(PBYTE)p->Name,&cb,0);
if (status == CR_SUCCESS)
{
if (PropertyType == DEVPROP_TYPE_STRING)
{
*pp = p;
return CR_SUCCESS;
}
else
{
status = CR_WRONG_TYPE;
}
}
delete p;
}
else
{
status = CR_OUT_OF_MEMORY;
}
} while (CR_BUFFER_SMALL == status);
return status;
}
CONFIGRET GetFriendlyNameByInterface(DeviceName** pp,PCWSTR pszDeviceInterface)
{
// RTCu must be disabled !
ULONG cb = 0,rcb = 64;
PVOID stack = alloca(guz);
DEVPROPTYPE PropertyType;
CONFIGRET status;
union {
PVOID pv;
PWSTR DeviceID;
PBYTE pb;
};
do
{
if (cb < rcb)
{
rcb = cb = RtlPointerToOffset(pv = alloca(rcb - cb),stack);
}
} while (CR_BUFFER_SMALL == (status = CM_Get_Device_Interface_PropertyW(
pszDeviceInterface,&DEVPKEY_Device_InstanceId,pb,&rcb,0)));
if (status == CR_SUCCESS)
{
if (PropertyType == DEVPROP_TYPE_STRING)
{
DEVINST dnDevInst;
status = CM_Locate_DevNodeW(&dnDevInst,DeviceID,CM_LOCATE_DEVNODE_NORMAL);
return status == CR_SUCCESS ? GetFriendlyNameByDevNode(pp,dnDevInst) : status;
}
else
{
status = CR_WRONG_TYPE;
}
}
return status;
}
case WM_DESTROY:
if (_hDevNot)
{
UnregisterDeviceNotification(_hDevNot);
PLIST_ENTRY head = &_DevListHead,entry = head->Flink;
while (entry != head)
{
DeviceName* p = static_cast<DeviceName*>(entry);
entry = entry->Flink;
delete p;
}
}
break;
case WM_DEVICECHANGE:
switch (wParam)
{
case DBT_DEVICEREMOVECOMPLETE:
case DBT_DEVICEARRIVAL:
if (reinterpret_cast<PDEV_BROADCAST_DEVICEINTERFACE>(lParam)->dbcc_devicetype == DBT_DEVTYP_DEVICEINTERFACE)
{
DeviceName* p;
ULONG InterfaceHash;
UNICODE_STRING dbcc_name;
RtlInitUnicodeString(&dbcc_name,reinterpret_cast<PDEV_BROADCAST_DEVICEINTERFACE>(lParam)->dbcc_name);
RtlHashUnicodeString(&dbcc_name,FALSE,HASH_STRING_ALGORITHM_DEFAULT,&InterfaceHash);
if (wParam == DBT_DEVICEARRIVAL)
{
if (CR_SUCCESS == GetFriendlyNameByInterface(&p,dbcc_name.Buffer))
{
p->InterfaceHash = InterfaceHash;
InsertHeadList(&_DevListHead,p);
DbgPrint("inserted %S ( %wZ )\n",p->Name,&dbcc_name);
}
}
else
{
PLIST_ENTRY head = &_DevListHead,entry = head;
while ((entry = entry->Flink) != head)
{
if (static_cast<DeviceName*>(entry)->InterfaceHash == InterfaceHash)
{
DbgPrint("removed %S ( %wZ )\n",static_cast<DeviceName*>(entry)->Name,&dbcc_name);
RemoveEntryList(entry);
delete static_cast<DeviceName*>(entry);
break;
}
}
}
}
break;
}
return 0;
case WM_CREATE:
InitializeListHead(&_DevListHead);
static DEV_BROADCAST_DEVICEINTERFACE dbd = { sizeof(dbd),DBT_DEVTYP_DEVICEINTERFACE };
_hDevNot = RegisterDeviceNotificationW(hwnd,DEVICE_NOTIFY_WINDOW_HANDLE|DEVICE_NOTIFY_ALL_INTERFACE_CLASSES);
break;
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。