ManagementEventWatcher теряет события в C#
Я разрабатываю приложение, которое использует ManagementEventWatcher
контролировать USB
События. Код работает правильно, но в некоторых случаях программа теряет некоторые USB events
, Как правильно составить список всех событий с USB?
Я использую следующий код, я использую два запроса для подключения монитора и отсоединения от USB. Мне нужно контролировать много портов USB.
USB-монитор
ManagementEventWatcher watchUSBattach = new ManagementEventWatcher();
ManagementEventWatcher watchUSBDettach = new ManagementEventWatcher();
WqlEventQuery queryUsbAttach = new WqlEventQuery("SELECT * FROM Win32_VolumeChangeEvent WHERE EventType = 2 ");
watchUSBattach.EventArrived += new EventArrivedEventHandler(watchUSBEventAdd);
watchUSBattach.Query = queryUsbAttach;
watchUSBattach.Start();
WqlEventQuery queryUsbDettach = new WqlEventQuery("SELECT * FROM Win32_VolumeChangeEvent WHERE EventType = 3");
watchUSBDettach.EventArrived += new EventArrivedEventHandler(watchUSBEventDettach);
watchUSBDettach.Query = queryUsbDettach;
watchUSBDettach.Start();
1 ответ
Я наблюдал аналогичную вещь при мониторинге для вставки или удаления USB-устройства. Пример кода ниже. Когда WithinInterval
свойство установлено на 1 мс, тогда я не пропускаю события, но вместо этого я испытываю необоснованную нагрузку на процессор в WMIProviderHost и связанной службе. Если я установлю более разумное значение, например 3 секунды, я пропущу события удаления / создания, если они происходят слишком быстро с одного устройства (например, если устройство перезагружается). Возможно с вашим запросом по умолчанию WithinInterval
слишком длинный и вызывает отбрасывание событий?
WqlEventQuery q;
var scope = new ManagementScope("root\\CIMV2")
{Options = {EnablePrivileges = true}};
q = new WqlEventQuery
{
EventClassName = "__InstanceCreationEvent",
WithinInterval = TimeSpan.FromMilliseconds(1),
Condition = @"TargetInstance ISA 'Win32_USBControllerdevice'"
};
InsertWatcher = new ManagementEventWatcher(scope, q);
InsertWatcher.EventArrived += (sender, args) =>
{
var instance = (ManagementBaseObject) args.NewEvent["TargetInstance"];
RaiseInserted(new PlugEventArgs {DevicePath = (string) instance["__PATH"]});
};
InsertWatcher.Start();