简体   繁体   中英

ManagementEventWatcher losting events in C#

I'm developing an application that uses ManagementEventWatcher to monitor USB events. The code works properly but in some cases the program lost some USB events . What is the correct way to list all events from USB?

I'm using the follow code, I'm using two queries for monitor attach and detach from usb. I need to monitor a many USB ports.

USB Monitor

    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();

I have experienced a similar thing when monitoring for usb device insertion or removal. Example code below. When the WithinInterval property is set to 1ms then I do not miss the events but instead I suffer an unreasonable CPU load in WMIProviderHost and the associated service. If I set it to a more reasonable value like 3 seconds then I miss Deletion/Creation events if they occur together from the same device too quickly (for example if the device resets itself). Perhaps with your query the default WithinInterval is too long and is causing events to be dropped?

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();

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM